﻿package Server.AHMJ.LAMJ;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Set;

class SanMj {
	public SanMj(int mj, int num) {
		m_mj = mj;
		m_num = num;
	}

	public int m_mj;
	public int m_num;
}

public class MajHelper {
	public static int hu_Index = -1;
	static int m_testMjPai[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, // 1-9 一万-九万
			11, 12, 13, 14, 15, 16, 17, 18, 19, // 11-19一筒-九筒
			21, 22, 23, 24, 25, 26, 27, 28, 29, // 21-29 一条-九条
			31, 32, 33, 34, 35, 36, 37 // 31-37 东南西北中发白
	};

	/**
	 * 用于拷贝一份牌出来 防止改变牌
	 * 
	 * @param handMj
	 * @return
	 */
	public static int[] copyHandMaj(int handMj[]) {
		int tmpHandMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(tmpHandMj, handMj, Constants.HAND_MJ_MAX);
		return tmpHandMj;
	}

	public static void SortCard(int byHandCard[], int byHandMjCount) {
		for (int i = 0; i < byHandMjCount - 1; i++) {
			for (int j = i; j < byHandMjCount; j++) {
				int x = byHandCard[i];
				int y = byHandCard[j];

				if (x > y) {
					int tempvalue = byHandCard[i];
					byHandCard[i] = byHandCard[j];
					byHandCard[j] = tempvalue;
				}
			}
		}
	}

	public static boolean IsGuiPai(int byMj, int byGuiPai[]) {
		if (MajHelper.IsWTSZ(byMj) == false) {
			return false;
		}
		for (int j = 0; j < byGuiPai.length; j++) {
			if (byMj == byGuiPai[j]) {
				return true;
			}
		}
		/*
		 * if (caiShen != Constants.INVALID_CARD) { if (caishenNum > 0) {
		 * 
		 * } else { int baiNum = 0; int[] OriginalMj1 = OriginalMj.clone(); for
		 * (int i = 0; i < OriginalMj1.length; i++) { int j = OriginalMj1[i]; if
		 * (j == Constants.bai) { OriginalMj1[i] = caiShen; baiNum++; } } if
		 * (baiNum > 0 && IsHu(OriginalMj1, byMj, hu, tempHu,
		 * Constants.INVALID_CARD)) { return true; } } }
		 */

		// 无财神情况
		return false;
	}

	public static boolean IsHu(int byHandMj[], int byMj, int caiShen,
			boolean bZiMo, ArrayList<HU> list) {
		return IsHu(byHandMj, byMj, new HU(), caiShen, bZiMo, list);
	}

	public static int GetRelativeSeat(int bySeatID, int byLastOutUser) {
		int currindex = bySeatID;
		int outindex = byLastOutUser;
		if (currindex == 3 && outindex == 0)
			outindex = 4;
		else if (currindex == 0 && outindex == 3)
			currindex = 4;
		if (currindex - outindex == 1)
			return 0;
		else if (outindex - currindex == 1)
			return 2;
		else
			return 1;
	}

	// ////////////////////////////////////////////////////////////////////////
	// 0-8 一万-九万
	// 9-17 一条-九条w
	// 18-26 一筒-九筒
	// 27-33 东南西北中发白
	// 34-41 春夏秋冬梅兰竹菊
	// ////////////////////////////////////////////////////////////////////////
	public static boolean IsHu(int byHandMj[], int byMj, HU hu, boolean bZiMo,
			ArrayList<HU> list) {
		return IsHu(byHandMj, byMj, hu, Constants.INVALID_CARD, bZiMo, list);
	}

	// int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
	// Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
	// if (byMj != Constants.INVALID_CARD) {
	// OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
	// }
	//
	// SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
	//
	// Constants.replace(OriginalMj, caishen, Constants.INVALID_CARD);
	// //Constants.replace(OriginalMj, bai, caishen);
	// SortCard(OriginalMj, Constants.HAND_MJ_MAX);
	// int tempMj[] = new int[Constants.HAND_MJ_MAX];
	// int tempMj2[] = new int[Constants.HAND_MJ_MAX];
	// // 将牌位在整数块( 0, 3, 6, 9, 12, 15 )处
	// // 设置变量
	// MJ_BLOCK block0 = null;
	// MJ_BLOCK block1 = null;
	// MJ_BLOCK block2 = null;
	// // if( IsJiang( tempMj[i], tempMj[i+1] ) )
	// {
	// // 胡牌结构处理
	//
	// for (int i = 0; i < Constants.HAND_MJ_MAX - 1; i++) {
	// Constants.memcpy(tempMj, OriginalMj, Constants.HAND_MJ_MAX);
	// HU out_hu = new HU();
	//
	// if (IsJiang(tempMj[i], tempMj[i + 1])) {
	// out_hu.jiangMj = tempMj[i];
	// tempMj[i] = Constants.INVALID_CARD;
	// tempMj[i + 1] = Constants.INVALID_CARD;
	// }
	// Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
	// SortCard(tempMj2, Constants.HAND_MJ_MAX);
	//
	// DG_HU(tempMj2, out_hu, list);
	// if (hu.jiangMj >= 31 || (hu.jiangMj % 10 != 1 && hu.jiangMj % 10 != 9)) {
/**
 * 判断是否为妖头 
 * @param jiangPai
 * @param sanMj
 * @param byActivePai
 * @return
 */
   public static boolean IsYaoTou(int jiangPai,int []sanMj,int byActivePai,int caiShen){
	   if(jiangPai!=255){
		   if ((jiangPai >= 31 && jiangPai <= 37) || (jiangPai % 10 == 1)
					|| (jiangPai % 10 == 9)) {
				 return true;
			}
	   }else{
		  if(byActivePai==caiShen){
			  List<Integer> list=new ArrayList<Integer>();
			  for(int i=0;i<sanMj.length-1;i++){
				  if(sanMj[i]==sanMj[i+1]){
					  list.add(sanMj[i]);
				  }
			  }
			  if(list!=null&&list.size()!=0){
				  for(int i=0;i<list.size();i++){
				     if ((list.get(i) >= 31 && list.get(i) <= 37) || (list.get(i) % 10 == 1)
									|| (list.get(i) % 10 == 9)) {
								  return true;
								  
					}
				  }
			  }
		  }
	   }
	   return false;
   }
	/**
	 * 断幺九 (手里是否有东南西北中发白和包含1,9)的牌
	 * 
	 * @param tempMj
	 * @param hu
	 * @param listGang
	 * @param listPong
	 * @return
	 */
	public static boolean IsDuanYaoJiu(int tempMj[], HU hu,
			List<BLOCK_GANGINFO> listGang, List<BLOCK_PONGINFO> listPong) {
		int gangFirst = 0;
		if (listGang != null && listGang.size() != 0) {
			for (int i = 0; i < listGang.size(); i++) {
				gangFirst = listGang.get(i).first;
				if (IsZi(gangFirst) || gangFirst % 10 == 1
						|| gangFirst % 10 == 9) {
					return false;
				}
			}
		}
		int pengFirst = 0;
		if (listPong != null && listPong.size() != 0) {
			for (int i = 0; i < listPong.size(); i++) {
				pengFirst = listPong.get(i).first;
				if (IsZi(pengFirst) || pengFirst % 10 == 1
						|| pengFirst % 10 == 9) {
					return false;
				}
			}
		}

		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (IsZi(tempMj[i]) || tempMj[i] % 10 == 1 || tempMj[i] % 10 == 9) {
				return false;
			}
		}
		return true;
	}

	/**
	 * 板板高 手中是否有连续的对子(并且对子能组成顺子)
	 * @param blocks
	 * @return
	 */
	public static int IsBanBanGao(BLOCK[] blocks) {
		List<Integer> blockFirst = new ArrayList<Integer>();
		for (int i = 0; i < blocks.length; i++) {
			if (blocks[i].style == 2) {
				blockFirst.add(blocks[i].first);
			}
		}
		Collections.sort(blockFirst);
		int bbg = 0;
		for (int i = 0; i < blockFirst.size() - 1;) {
			if (blockFirst.get(i) == blockFirst.get(i + 1)) {
				bbg++;
				i += 2;
			} else {
				i++;
			}
		}
		return bbg;
	}

	/**
	 * 统计每个玩家碰和杠的总次数。补杠和碰的重复需要去掉
	 * 
	 * @param listGang
	 * @param listPong
	 * @return
	 */
	public static int countPengAndGang(List<BLOCK_GANGINFO> listGang,
			List<BLOCK_PONGINFO> listPong) {
		int repeatCount = 0;
		for (int i = 0; i < listGang.size(); i++) {
			for (int j = 0; j < listPong.size(); j++) {
				if (listGang.get(i).first - listPong.get(j).first == 0) {
					repeatCount++;
				}
			}
		}
		int sumPengAngGang = listPong.size() + listGang.size() - repeatCount;
		return sumPengAngGang;
	}

	/**
	 * @param listGang
	 *            杠的集合
	 * @param listPong
	 *            碰的集合
	 * @return
	 */
	public static int countPeng(List<BLOCK_GANGINFO> listGang,
			List<BLOCK_PONGINFO> listPong) {
		int repeatCount = 0;
		for (int i = 0; i < listGang.size(); i++) {
			for (int j = 0; j < listPong.size(); j++) {
				if (listGang.get(i).first - listPong.get(j).first == 0) {
					repeatCount++;
				}
			}
		}
		int pengCount = listPong.size() - repeatCount;
		return pengCount;
	}

	/**
	 * 缺门(手中是否缺一门,东南西北中发白不算)
	 * 
	 * @param byHandMj
	 * @param listGang
	 * @param listPong
	 * @return
	 */
	public static int QueMen(int byHandMj[],int caiShen, List<BLOCK_GANGINFO> listGang,
			List<BLOCK_PONGINFO> listPong) {
		int [] handMj=getPai(byHandMj,caiShen);
		// 统计手中的万筒条
		int wanCount = 0;
		int tongCount = 0;
		int tiaoCount = 0;
		for (int i = 0; i < handMj.length; i++) {
			if (IsWan(handMj[i])) {
				wanCount++;
			}
			if (IsTong(handMj[i])) {
				tongCount++;
			}
			if (IsSuo(handMj[i])) {
				tiaoCount++;
			}
		}
		// 统计杠牌的数量
		int wanGangCount = 0;
		int tongGangCount = 0;
		int tiaoGangCount = 0;
		for (BLOCK_GANGINFO gangInfo : listGang) {
			if (IsWan(gangInfo.first)) {
				wanGangCount++;
			}
			if (IsTong(gangInfo.first)) {
				tongGangCount++;
			}
			if (IsSuo(gangInfo.first)) {
				tiaoGangCount++;
			}
		}

		// 统计碰牌的数量
		int wanPengCount = 0;
		int tongPengCount = 0;
		int tiaoPengCount = 0;
		for (BLOCK_PONGINFO pengInfo : listPong) {
			if (IsWan(pengInfo.first)) {
				wanPengCount++;
			}
			if (IsTong(pengInfo.first)) {
				tongPengCount++;
			}
			if (IsSuo(pengInfo.first)) {
				tiaoPengCount++;
			}
		}
		int wanSum = wanCount + wanGangCount + wanPengCount;
		int tongSum = tongCount + tongGangCount + tongPengCount;
		int tiaoSum = tiaoCount + tiaoGangCount + tiaoPengCount;
		// 缺一门
		if ((wanSum >= 1 && tongSum >= 1 && tiaoSum == 0)
				|| (wanSum >= 1 && tiaoSum >= 1 && tongSum == 0)
				|| (tongSum >= 1 && tiaoSum >= 1 && wanSum == 0)) {

			return 1;
		}
		// 缺两门
		if ((wanSum >= 1 && tongSum == 0 && tiaoSum == 0)
				|| (tiaoSum >= 1 && wanSum == 0 && tongSum == 0)
				|| (tongSum >= 1 && tiaoSum == 0 && wanSum == 0)) {

			return 2;
		}
		return 0;

	}

	/**
	 * 判断 四活(坎子加双铺算四活,对子加铺也算四活)
	 * 
	 * @param handMj
	 * @param caiShen
	 * @return
	 */
	public static int IsSiHuo(int handMj[], int caiShen, int byMj,
			List<BLOCK_PONGINFO> listPong) {
		// 判断四活
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, handMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
		}
		SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
		int countSiHuo = 0;
		// 统计碰和手中牌
		int b = 0;
		int countPengSiHuo = 0;
		List<Integer> listFirst = new ArrayList<Integer>();
		for (int i = 0; i < listPong.size(); i++) {
			if (listPong.get(i).first <= 29) {
				listFirst.add(listPong.get(i).first);
			}
		}
		for (int j = 0; j < OriginalMj.length; j++) {
			if (OriginalMj[j] != 255) {
				if (listFirst.contains(OriginalMj[j])) {
					countPengSiHuo++;

				}
			}

		}

		for (int i = 0; i < OriginalMj.length; i++) {
			int a = 0;
			if (OriginalMj[i] != 255 && a <= 29) {
				a = OriginalMj[i];
			}
			int countPai = 0;
			if (a != caiShen) {
				countPai = Constants.countof(OriginalMj, a);
			}
			if (countPai == 4) {
				countSiHuo++;
				i += 3;
			}

		}
		int sumSiHuo = countPengSiHuo + countSiHuo;
		return sumSiHuo;
	}

	/**
	 * 有包独子
	 * 
	 * @param sanMj
	 * @param byActivePai
	 * @return
	 */
	public static boolean IsDuZi(int[] handmjs, HU hu,BLOCK[] blocks, int byActivePai, int caiShen) {
		if(hu == null)
			return false;
		int cscount = 0;
		cscount  = Constants.countof(handmjs,caiShen);
		if(cscount == 0)
			return false;
		int blockFirst = 0;
		List<Integer> firstList = new ArrayList<Integer>();
		for (int i = 0; i < blocks.length; i++) {
			if (blocks[i].style == 2) {
				blockFirst = blocks[i].first;
				firstList.add(blockFirst);
			}
		}
		for (int i = 0; i < firstList.size(); i++) {
			if (MajHelper.IsTongHuaSe(firstList.get(i), byActivePai)) {
				if (byActivePai - firstList.get(i) == 1) {
					return true;
				}
				if (byActivePai % 10 == 3) {
					if (byActivePai - firstList.get(i) == 2) {
						return true;
					}
				}
				if (byActivePai % 10 == 7) {
					if (byActivePai == firstList.get(i)) {
						return true;
					}
				}
			}
		}
		firstList.clear();
		if(byActivePai != caiShen)
			return false;
		ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
		if (hu.jiangMj == 255)
			RemoveAlikeJiang(dzmj);
		ArrayList<BLOCK> sanBlock = ChangeToBaoPaiDuZi(dzmj, caiShen);
		if(sanBlock.size() > 0)
			return true;
		return false;
	}
	/**
	 * 判断无宝独子
	 * @param byHandMj
	 * @param blocks
	 * @param byActivePai
	 * @param caiShen
	 * @return
	 */

	public static boolean IsWuBaoDuZi(int[] handmj,HU hu,int byHandMj[],BLOCK[] blocks, int byActivePai, int caiShen){
		if(hu == null)
			return false;
		int csCount = Constants.countof(handmj, caiShen);
		if(csCount != 0)
			return false;
		int blockFirst = 0;
		List<Integer> firstList = new ArrayList<Integer>();
		for (int i = 0; i < blocks.length; i++) {
			if (blocks[i].style == 2) {
				blockFirst = blocks[i].first;
				firstList.add(blockFirst);
			}
		}
		for (int i = 0; i < firstList.size(); i++) {
			if (MajHelper.IsTongHuaSe(firstList.get(i), byActivePai)) {
				if (byActivePai - firstList.get(i) == 1) {
					return true;
				}
				if (byActivePai % 10 == 3) {
					if (byActivePai - firstList.get(i) == 2) {
						return true;
					}
				}
				if (byActivePai % 10 == 7) {
					if (byActivePai == firstList.get(i)) {
						return true;
					}
				}
			}
		}
		return false;
	}
 

	/**
	 * 清风(手中全是东南西北中发白的胡牌，宝牌必须归位吗，不能配，红中可以替宝)
	 * 
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static boolean IsQingFeng(int byHandMj[], int byMj, HU hu,
			int caiShen, boolean bZiMo, ArrayList<HU> list,
			List<BLOCK_GANGINFO> gangList, List<BLOCK_PONGINFO> pengList) {
		if (caiShen < 31 && caiShen > 0) {
			// 红中替宝的数量必须为0
			int hongZhongTiBaoCount = GetHZTiBaoCount(byHandMj, byMj, hu,
					caiShen);
			if (hongZhongTiBaoCount == 0) {
				return IsPaiXingQingFeng(byHandMj, hu, caiShen, gangList,
						pengList);
			}
		}
		if (Constants.countof(byHandMj, caiShen) > 0) {
			if (IsQuanBGW(byHandMj, byMj, hu, caiShen) == 1) {
				return IsPaiXingQingFeng(byHandMj, hu, caiShen, gangList,
						pengList);
			}
		} else {
			return IsPaiXingQingFeng(byHandMj, hu, caiShen, gangList, pengList);
		}

		return false;
	}

	public static boolean IsPaiXingQingFeng(int tempMj[], HU hu, int caiShen,
			List<BLOCK_GANGINFO> gangList, List<BLOCK_PONGINFO> pengList) {
		// 统计手中的万筒条
		int wanCount = 0;
		int tongCount = 0;
		int tiaoCount = 0;
		int fengCount = 0;
		for (int i = 0; i < tempMj.length; i++) {
			if (IsWan(tempMj[i])) {
				wanCount++;
			}
			if (IsTong(tempMj[i])) {
				tongCount++;
			}
			if (IsSuo(tempMj[i])) {
				tiaoCount++;
			}
			if (IsZi(tempMj[i])) {
				fengCount++;
			}

		}
		// 统计杠牌的数量
		int wanGangCount = 0;
		int tongGangCount = 0;
		int tiaoGangCount = 0;
		int fengGangCount = 0;
		for (BLOCK_GANGINFO gangInfo : gangList) {
			if (IsWan(gangInfo.first)) {
				wanGangCount++;
			}
			if (IsTong(gangInfo.first)) {
				tongGangCount++;
			}
			if (IsSuo(gangInfo.first)) {
				tiaoGangCount++;
			}
			if (IsZi(gangInfo.first)) {
				fengGangCount++;
			}
		}
		// 统计碰牌的数量
		int wanPengCount = 0;
		int tongPengCount = 0;
		int tiaoPengCount = 0;
		int fengPengCount = 0;
		for (BLOCK_PONGINFO pengInfo : pengList) {
			if (IsWan(pengInfo.first)) {
				wanPengCount++;
			}
			if (IsTong(pengInfo.first)) {
				tongPengCount++;
			}
			if (IsSuo(pengInfo.first)) {
				tiaoPengCount++;
			}
			if (IsZi(pengInfo.first)) {
				fengPengCount++;
			}
		}
		int wanSum = wanCount + wanGangCount + wanPengCount;
		int tongSum = tongCount + tongGangCount + tongPengCount;
		int tiaoSum = tiaoCount + tiaoGangCount + tiaoPengCount;
		int fengSum = fengCount + fengGangCount + fengPengCount;
		if (fengSum > 0) {
			if ((wanSum == 0 && tongSum == 0 && tiaoSum == 0)) {
				return true;
			}
		}
		return false;
	}
	
	/**
	 * 遍历手中除了宝牌剩下的牌
	 * @param byHandMj
	 * @param caiShen
	 * @return
	 */
	public static int [] getPai(int byHandMj[],int caiShen){
	//手中的牌放到list当中
	List<Integer> paiList=new ArrayList<Integer>();
	for (int i = 0; i < byHandMj.length; i++) {
		if(byHandMj[i]!=255){
		paiList.add(byHandMj[i]);
		}
	}
	 for(int i=0;i<paiList.size();i++){
		 if(paiList.get(i)==caiShen){
			 paiList.remove(i);
			 i--;
		 }
	 }
	Integer[] mjs = paiList.toArray(new Integer[0]);
	 int[] mjs2 = new int[mjs.length];
	 for(int i=0;i<mjs.length;i++){
	    mjs2[i] = mjs[i];
	 }
	    return mjs2;
 }
	/**
	 * 混一色 宝牌必须归位，但是不能配，红中可以替宝
	 * 
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static boolean IsHunYiSe(int byHandMj[], int byMj, HU hu,
			int caiShen, boolean bZiMo, ArrayList<HU> list,
			List<BLOCK_GANGINFO> gangList, List<BLOCK_PONGINFO> pengList) {
			return IsPaiXinHunYiSe(byHandMj, hu, caiShen, gangList, pengList);

	}

	// 混一色
	public static boolean IsPaiXinHunYiSe(int tempMj[], HU hu, int zhenCaiShen,
			List<BLOCK_GANGINFO> gangList, List<BLOCK_PONGINFO> pengList) {
	 	    tempMj = copyHandMaj(tempMj);
		  int []remaining  =getPai(tempMj,zhenCaiShen);
		// 统计手中的万筒条
		int wanCount = 0;
		int tongCount = 0;
		int tiaoCount = 0;
		int fengCount = 0;
		for (int i = 0; i < remaining.length; i++) {
			if (IsWan(remaining[i])) {
				wanCount++;
			}
			if (IsTong(remaining[i])) {
				tongCount++;
			}
			if (IsSuo(remaining[i])) {
				tiaoCount++;
			}
			if (IsZi(remaining[i])) {
				fengCount++;
			}

		}
		// 统计杠牌的数量
		int wanGangCount = 0;
		int tongGangCount = 0;
		int tiaoGangCount = 0;
		int fengGangCount = 0;
		for (BLOCK_GANGINFO gangInfo : gangList) {
			if (IsWan(gangInfo.first)) {
				wanGangCount++;
			}
			if (IsTong(gangInfo.first)) {
				tongGangCount++;
			}
			if (IsSuo(gangInfo.first)) {
				tiaoGangCount++;
			}
			if (IsZi(gangInfo.first)) {
				fengGangCount++;
			}
		}

		// 统计碰牌的数量
		int wanPengCount = 0;
		int tongPengCount = 0;
		int tiaoPengCount = 0;
		int fengPengCount = 0;
		for (BLOCK_PONGINFO pengInfo : pengList) {
			if (IsWan(pengInfo.first)) {
				wanPengCount++;
			}
			if (IsTong(pengInfo.first)) {
				tongPengCount++;
			}
			if (IsSuo(pengInfo.first)) {
				tiaoPengCount++;
			}
			if (IsZi(pengInfo.first)) {
				fengPengCount++;
			}
		}
		int wanSum = wanCount + wanGangCount + wanPengCount;
		int tongSum = tongCount + tongGangCount + tongPengCount;
		int tiaoSum = tiaoCount + tiaoGangCount + tiaoPengCount;
		int fengSum = fengCount + fengGangCount + fengPengCount;
		if (fengSum > 0) {
			if ((wanSum >= 1 && tongSum == 0 && tiaoSum == 0)
					|| (tiaoSum >= 1 && wanSum == 0 && tongSum == 0)
					|| (tongSum >= 1 && tiaoSum == 0 && wanSum == 0)) {

				return true;
			}
		}
		return false;
	}

	/**
	 * 清一色 宝牌必须归位，但是不能配，红中可以替宝
	 * 
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return IsPaiXinHunYiSe
	 */
	public static boolean IsQingYiSe(int byHandMj[], int byMj, HU hu,
			int caiShen, boolean bZiMo, ArrayList<HU> list,
			List<BLOCK_GANGINFO> gangList, List<BLOCK_PONGINFO> pengList) {
			return IsPaiXinQingYiSe(byHandMj, hu, caiShen, gangList, pengList);
		
	}

	/**
	 * 牌型清一色
	 * 
	 * @param tempMj
	 * @param hu
	 * @param zhenCaiShen
	 * @param gangList
	 * @param pengList
	 * @return
	 */
	public static boolean IsPaiXinQingYiSe(int tempMj[], HU hu,
			int zhenCaiShen, List<BLOCK_GANGINFO> gangList,
			List<BLOCK_PONGINFO> pengList) {
		tempMj = copyHandMaj(tempMj);
		
		 int [] remaining=getPai(tempMj,zhenCaiShen);
		// 统计手中的万筒条
		int wanCount = 0;
		int tongCount = 0;
		int tiaoCount = 0;
		int fengCount = 0;
		for (int i = 0; i < remaining.length; i++) {
			if (IsWan(remaining[i])) {
				wanCount++;
			}
			if (IsTong(remaining[i])) {
				tongCount++;
			}
			if (IsSuo(remaining[i])) {
				tiaoCount++;
			}
			if (IsZi(remaining[i])) {
				fengCount++;
			}

		}
		// 统计杠牌的数量
		int wanGangCount = 0;
		int tongGangCount = 0;
		int tiaoGangCount = 0;
		int fengGangCount = 0;
		for (BLOCK_GANGINFO gangInfo : gangList) {
			if (IsWan(gangInfo.first)) {
				wanGangCount++;
			}
			if (IsTong(gangInfo.first)) {
				tongGangCount++;
			}
			if (IsSuo(gangInfo.first)) {
				tiaoGangCount++;
			}
			if (IsZi(gangInfo.first)) {
				fengGangCount++;
			}
		}

		// 统计碰牌的数量
		int wanPengCount = 0;
		int tongPengCount = 0;
		int tiaoPengCount = 0;
		int fengPengCount = 0;
		for (BLOCK_PONGINFO pengInfo : pengList) {
			if (IsWan(pengInfo.first)) {
				wanPengCount++;
			}
			if (IsTong(pengInfo.first)) {
				tongPengCount++;
			}
			if (IsSuo(pengInfo.first)) {
				tiaoPengCount++;
			}
			if (IsZi(pengInfo.first)) {
				fengPengCount++;
			}
		}
		int wanSum = wanCount + wanGangCount + wanPengCount;
		int tongSum = tongCount + tongGangCount + tongPengCount;
		int tiaoSum = tiaoCount + tiaoGangCount + tiaoPengCount;
		int fengSum = fengCount + fengGangCount + fengPengCount;
		if (fengSum == 0) {
			if ((wanSum >= 1 && tongSum == 0 && tiaoSum == 0)
					|| (tiaoSum >= 1 && wanSum == 0 && tongSum == 0)
					|| (tongSum >= 1 && tiaoSum == 0 && wanSum == 0)) {

				return true;
			}
		}
		return false;

	}

	// 判断红中替包的个数
	public static int GetHZTiBaoCount(int byHandMj[], int byMj, HU hu, int cs) {
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[13] == Constants.INVALID_CARD) {
			OriginalMj[13] = byMj;
		}
		int hzCount = Constants.countof(byHandMj, 35);
		if (hzCount == 0)
			return 0;
		int csCount = Constants.countof(byHandMj, cs);
		int tbCount = hzCount;
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		for (int i = 0; i < 4; i++) {
			BLOCK block = hu.block[i];
			if (block.first != 0) {
				blocks.add(block);
			}
		}
		ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
		if (hu.jiangMj == 255) {
			int mj = GetAlikeJiang(dzmj);
			if (mj == 35) {
				tbCount -= 2;
			}
			RemoveAlikeJiang(dzmj);
		}
		for (int i = 0; i < blocks.size(); i++) {
			BLOCK block = blocks.get(i);
			if (block.style == 2) {
				if (cs >= block.first && Math.abs(cs - block.first) <= 2)
					tbCount--;
			} else if (block.style == 4) {
				if (block.first == cs) {
					tbCount -= 3;
				}
			}
		}
		ArrayList<BLOCK> sanBlock = ChangeToBaoPaiShunZiKeZi(dzmj, cs);
		for (int i = 0; i < sanBlock.size(); i++) {
			BLOCK block = sanBlock.get(i);
			if (block.style == 2) {
				// 顺子
				if (block.origValue == cs) {
					tbCount--;
				}
			} else if (block.style == 4) {
				if (block.origValue == cs) {
					if (csCount == 1) {
						tbCount -= 2;
					} else {
						tbCount -= 1;
					}
				}
			}
		}
		if (tbCount <= 0) {
			return hzCount;
		} else {
			return hzCount - tbCount;
		}
	}

	// 判断是否全部宝归位
	// 0:表示没有宝牌
	// 1:表示全部宝归位
	// -1:表示没有全部归位
	public static int IsQuanBGW(int byHandMj[], int byMj, HU hu, int cs) {
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[13] == Constants.INVALID_CARD) {
			OriginalMj[13] = byMj;
		}
		int csCount = Constants.countof(OriginalMj, cs);
		if (csCount != 0) {
			ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
			if (hu.jiangMj == 255)
				RemoveAlikeJiang(dzmj);
			ArrayList<BLOCK> sanBlock = ChangeToBaoPaiShunZiBGW(dzmj, cs);
			int gwCount = 0;
			for (int i = 0; i < sanBlock.size(); i++) {
				BLOCK block = sanBlock.get(i);
				if (Math.abs(block.first - cs) <= 2) {
					gwCount++;
				}
			}
			if (gwCount != csCount)
				return -1;
			else
				return 1;
		} else {
			return 0;
		}
	}

	// 判断是否有宝归位
	public static boolean HasBGW(int byHandMj[], int byMj, HU hu, int cs) {
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[13] == Constants.INVALID_CARD) {
			OriginalMj[13] = byMj;
		}
		int csCount = Constants.countof(OriginalMj, cs);
		if (csCount != 0) {
			ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
			if (hu.jiangMj == 255)
				RemoveAlikeJiang(dzmj);
			ArrayList<BLOCK> sanBlock = ChangeToBaoPaiShunZiBGW(dzmj, cs);
			int gwCount = 0;
			for (int i = 0; i < sanBlock.size(); i++) {
				BLOCK block = sanBlock.get(i);
				if (Math.abs(block.first - cs) <= 2) {
					gwCount++;
				}
			}
			if (gwCount > 0)
				return true;
			else
				return false;
		} else {
			return false;
		}
	}

	/**
	 * 判断一条龙(宝牌可以归位但是不能替，红中可以替宝牌)
	 * 
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static boolean IsYiTiaoLong(int byHandMj[], int byMj, HU hu, int cs) {
//		int bgw = IsQuanBGW(byHandMj, byMj, hu, cs);
//		if (bgw < 0)
//			return false;
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		for (int i = 0; i < 4; i++) {
			BLOCK block = hu.block[i];
			if (block.first != 0 && block.style == 2) {
				blocks.add(block);
			}
		}
		ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
		if (hu.jiangMj == 255)
			RemoveAlikeJiang(dzmj);
		ArrayList<BLOCK> sanBlock = ChangeToBaoPaiShunZiAny(dzmj, cs);
		for (int i = 0; i < sanBlock.size(); i++) {
			blocks.add(sanBlock.get(i));
		}
		// 开始搜索
		int[] nums = new int[9];
		for (int i = 0; i < blocks.size(); i++) {
			BLOCK block = blocks.get(i);
			if (block.first == 1)
				nums[0] = 1;
			else if (block.first == 4)
				nums[1] = 1;
			else if (block.first == 7)
				nums[2] = 1;
			else if (block.first == 11)
				nums[3] = 1;
			else if (block.first == 14)
				nums[4] = 1;
			else if (block.first == 17)
				nums[5] = 1;
			else if (block.first == 21)
				nums[6] = 1;
			else if (block.first == 24)
				nums[7] = 1;
			else if (block.first == 27)
				nums[8] = 1;
		}
		if (nums[0] == 1 && nums[1] == 1 && nums[2] == 1)
			return true;
		if (nums[3] == 1 && nums[4] == 1 && nums[5] == 1)
			return true;
		if (nums[6] == 1 && nums[7] == 1 && nums[8] == 1)
			return true;
		return false;
	}

	public static boolean IsMjCardMinSun(int card) {
		return card == 1 || card == 11 || card == 21;
	}

	public static boolean IsMjCardMiddSun(int card) {
		return card == 4 || card == 14 || card == 24;
	}

	public static boolean IsMjCardMaxSun(int card) {
		return card == 7 || card == 17 || card == 27;
	}

	private static int MjType_Wan = 1;
	private static int MJType_Tong = 2;
	private static int MjType_Suo = 3;
	private static int MJType_Zi = 4;

	public static int getMjType(int mj) {
		if (mj >= 1 && mj <= 9)
			return MjType_Wan;
		else if (mj >= 11 && mj <= 19)
			return MJType_Tong;
		else if (mj >= 21 && mj <= 29)
			return MjType_Suo;
		else
			return MJType_Zi;
	}

	/**
	 * 判断是否调宝
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static int IsDiaoBao(int byHandMj[], int byMj, HU hu, int caiShen,
			boolean bZiMo, ArrayList<HU> list) {
		if(hu == null)
			return 0;
		int csCount = Constants.countof(byHandMj,caiShen,13);
		if(csCount == 0)
			return 0;
		if(csCount == 1){
			int nohasmj = findRandMjNoInHandNoCs(byHandMj,caiShen);
			byMj = nohasmj;
			int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
			Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
			OriginalMj[13] = byMj;
			
			ArrayList<HU> newlist = new ArrayList<HU>();
			HU newhu = new HU();
			if (IsHu(OriginalMj, byMj, newhu, caiShen, bZiMo, newlist)) {
				return 5;
			}else{
				return 0;
			}
		}else{
			ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
			 boolean hasJiang = false;
			if (hu.jiangMj == 255){
				int count = dzmj.size();
				RemoveAlikeJiang(dzmj);
				hasJiang = dzmj.size() == count ? true:false;
			}
			
			int csNeed = ChangeToBaoPaiNum(dzmj, caiShen,hasJiang,byMj);
			int diff = csCount - csNeed;
			if(diff <= 0){
				if(byHandMj[byHandMj.length - 1] == byMj){
					//多个财神多判断一次
					int mj = findRandMjNoInHand(byHandMj);
					if(mj > 0){
						int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
						Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
						
						OriginalMj[OriginalMj.length - 1] = mj;
						HU hu1 = new HU();
						ArrayList<HU> newlist = new ArrayList<HU>();
						boolean IsHu = MajHelper.IsHu(OriginalMj, mj,hu1, caiShen, bZiMo, newlist);
						boolean hongZhongTiBaoHu = false;
						if (!IsHu) {
							// 红中替宝胡
							list.clear();
							hongZhongTiBaoHu = MajHelper.HongZongTibaoHu(OriginalMj, mj,hu1, caiShen, bZiMo,
									list);
						}
						if(IsHu || hongZhongTiBaoHu)
							return 5;
					}
				}
				return 0;
			}else if(diff == 1)
				return 5;
			else
				return 10;
		}
		 
 
	}
	
	/**
	 * 
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
//    public static int shuangDiaoBao(int byHandMj[], int byMj, HU hu, int caiShen,
//			boolean bZiMo, ArrayList<HU> list){
//    	
//    }
	public static int findRandMjNoInHandNoCs(int byHandMj[],int cs){
		for (int i = 0; i < m_testMjPai.length; i++) {
			boolean found = false;
			for (int k = 0; k < byHandMj.length; k++) {
				if (m_testMjPai[i] == byHandMj[k] || cs == m_testMjPai[i]
						|| Math.abs(byHandMj[k] - m_testMjPai[i]) <= 1) {
					found = true;
					break;
				}
			}
			if (found) {
				continue;
			} else {
				return m_testMjPai[i];
			}
		}
		return 0;
	}
	public static int findRandMjNoInHand(int byHandMj[]) {
		for (int i = 0; i < m_testMjPai.length; i++) {
			boolean found = false;
			for (int k = 0; k < byHandMj.length; k++) {
				if (m_testMjPai[i] == byHandMj[k]
						|| Math.abs(byHandMj[k] - m_testMjPai[i]) <= 1) {
					found = true;
					break;
				}
			}
			if (found) {
				continue;
			} else {
				return m_testMjPai[i];
			}
		}
		return 0;
	}

	// public static int IsShiSanLan(int byHandMj[],int byMj, HU hu, int
	// caiShen,boolean bZiMo, ArrayList<HU> list){
	// int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
	// Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
	// if (byMj != Constants.INVALID_CARD && OriginalMj[Constants.HAND_MJ_MAX -
	// 1] == Constants.INVALID_CARD) {
	// OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
	// }
	// SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
	//
	//
	// //拆牌
	// List<Integer> baoList=new ArrayList<Integer>();
	// List<Integer> hongZhongList=new ArrayList<Integer>();
	// List<Integer> otherList=new ArrayList<Integer>();
	// for(int i=0;i<OriginalMj.length;i++){
	// int current = OriginalMj[i];
	// if(current==Constants.INVALID_CARD){
	// return 0;
	// }else if(current==caiShen){
	// baoList.add(current);
	// }else if(current==35){
	// hongZhongList.add(current);
	// }else{
	// otherList.add(current);
	// }
	// }
	//
	// // 处理红中
	// if(hongZhongList.size()>=3){
	// return 0;
	// }
	// if(hongZhongList.size()==2){
	// //hongZhongList.remove(35);
	// otherList.add(35);
	// otherList.add(caiShen);
	// }
	// if(hongZhongList.size()==1){
	// otherList.add(35);
	// // do nothing
	// //红中为1的状况
	// //1.宝牌不是风牌，只能替风牌
	// //除了宝牌。风牌剩下的个数
	//
	// //宝牌是风牌。只能归位
	// }
	//
	// // 分 字 和 风
	// Map<Integer, Integer> fengCounts = new HashMap<Integer, Integer>();
	// Map<Integer, Integer> commonCounts = new HashMap<Integer, Integer>();
	// for(int i=0;i<otherList.size();i++){
	// Integer current = otherList.get(i);
	// if(IsZi(current)){
	// Integer fengCount = fengCounts.get(current);
	// fengCounts.put(current, fengCount==null?1:fengCount+1);
	// }else{
	// Integer commonCount = commonCounts.get(current);
	// commonCounts.put(current, commonCount==null?1:commonCount+1);
	// }
	// }
	//
	// for(Integer feng : fengCounts.keySet()){
	// Integer fengCount = fengCounts.get(feng);
	// if(fengCount>=2){
	// return 0;
	// }
	// }
	//
	// if(IsZi(caiShen) && baoList.size()>=2){
	// return 0;
	// }
	//
	// int duoyuBao = baoList.size() - (7- fengCounts.size());
	// if(duoyuBao>1){
	// return 0;
	// }
	//
	//
	// if(duoyuBao==1){
	// int csc = commonCounts.containsKey(caiShen) ? commonCounts.get(caiShen) :
	// 0;
	// commonCounts.put(caiShen, csc + 1 );
	// }
	//
	// List<Integer> commons = new ArrayList<Integer>();
	// for(Integer mj: commonCounts.keySet()){
	// Integer count = commonCounts.get(mj);
	// for(int i=0;i<count;i++){
	// commons.add(mj);
	// }
	// }
	// Collections.sort(commons);
	//
	//
	// Integer[] mjs = commons.toArray(new Integer[0]);
	//
	// int[] mjs2 = new int[mjs.length];
	// for(int i=0;i<mjs.length;i++){
	// mjs2[i] = mjs[i];
	// }
	//
	//
	// return shiSanLan(mjs2);
	// }
	//
	
	/**
	 * 统计红中的个数 包括碰和杠
	 * 
	 * @param byHandMj
	 * @param gangList
	 * @param pengList
	 * @return
	 */
	public static int countHongZhong(int byHandMj[], int byMj,
			List<BLOCK_GANGINFO> gangList, List<BLOCK_PONGINFO> pengList) {
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
		}
		SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
		int handHongZhong = 0;
		// 遍历手中红中的个数
		for (int i = 0; i < OriginalMj.length; i++) {
			if (OriginalMj[i] == 35) {
				handHongZhong++;
			}
		}
		// 统计碰牌
		int pengHongZhong = 0;
		for (int i = 0; i < pengList.size(); i++) {
			if (pengList.get(i).first == 35) {
				pengHongZhong = 3;
			}
		}
		for (int k = 0; k < gangList.size(); k++) {
			if (gangList.get(k).first == 35) {
				pengHongZhong = 4;
			}
		}
		
		// 遍历碰牌红中的个数
		for (int k = 0; k < pengList.size(); k++) {
			for (int i = 0; i < gangList.size(); i++) {
				if (gangList.get(i).first == 35 && pengList.get(k).first == 35) {
					pengHongZhong = 4;
				}
			}
		}
		return handHongZhong + pengHongZhong;

	}

	/**
	 * 判断是否的十三烂(手中的牌全不靠,红中不允许替宝，宝牌也不能替)
	 * @param byHandMj
	 * @param byMj
	 * @param caiShen
	 * @param hu
	 * @param list
	 * @return
	 */
	public static int IsShiSanLan(int byHandMj[], int byMj, HU hu, int caiShen,
			boolean bZiMo, ArrayList<HU> list) {
		// 把牌拷贝出来
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
		}
		SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
		for (int i = 0; i < OriginalMj.length; i++) {
			if (OriginalMj[i] == 255) {
				return 0;
			}
		}
		//手中的牌放到list当中
		List<Integer> paiList=new ArrayList<Integer>();
	 
		for (int i = 0; i < OriginalMj.length; i++) {
			paiList.add(OriginalMj[i]);
		}
		 for(int i=0;i<paiList.size();i++){
			 if(paiList.get(i)==caiShen){
				 paiList.remove(i);
				 i--;
			 }
		 }
		Integer[] mjs = paiList.toArray(new Integer[0]);
		 int[] mjs2 = new int[mjs.length];
		 for(int i=0;i<mjs.length;i++){
		    mjs2[i] = mjs[i];
		 }
		 //十三烂
		if (shiSanLan(mjs2)) {
			return 10;
		}
		return 0;
	}
   
	/**
	 * 判断十三烂缺一门
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static int IsShiSanLanQueYiMen(int byHandMj[], int byMj, HU hu, int caiShen,
			boolean bZiMo, ArrayList<HU> list){
		if(IsShiSanLan(byHandMj,byMj,hu,caiShen,bZiMo,list)==10){
			int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
			Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
			if (byMj != Constants.INVALID_CARD
					&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
				OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
			}
			SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
			//手中的牌放到list当中
			List<Integer> paiList=new ArrayList<Integer>();
		 
			for (int i = 0; i < OriginalMj.length; i++) {
				paiList.add(OriginalMj[i]);
			}
			 for(int i=0;i<paiList.size();){
				 if(paiList.get(i)==caiShen){
					 paiList.remove(i);
				 }else{
					 i++;
				 }
			 }
			Integer[] mjs = paiList.toArray(new Integer[0]);
			 int[] mjs2 = new int[mjs.length];
			 for(int i=0;i<mjs.length;i++){
			    mjs2[i] = mjs[i];
			 }
			 if(shiSanLanQueYiMen(mjs2)==20){
				 return 20;
			 }
		}
		return 0;
	}
	
	/**
	 * 十三烂七风全
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static int shiSanLanQiFengQuan(int byHandMj[], int byMj, HU hu, int caiShen,
			boolean bZiMo, ArrayList<HU> list){
		
		if(IsShiSanLan(byHandMj,byMj,hu,caiShen,bZiMo,list)==10){
			int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
			Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
			if (byMj != Constants.INVALID_CARD
					&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
				OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
			}
			SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
			//手中的牌放到list当中
			List<Integer> paiList=new ArrayList<Integer>();
			for(int i = 0;i < byHandMj.length;i++)
				paiList.add(byHandMj[i]);
		   boolean qiFengQuan=(paiList.contains(31)&&paiList.contains(32)&&paiList.contains(33)&&paiList.contains(34)
				   &&paiList.contains(35)&&paiList.contains(36)&&paiList.contains(37));
		   if(qiFengQuan){
			   return 20;
		   }

		}
		return 0;
		
	}
	/**
	 * 十三烂七风全 缺门
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static int shiSanLanQiFengQuanQueMen(int byHandMj[], int byMj, HU hu, int caiShen,
			boolean bZiMo, ArrayList<HU> list){
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
		}
		SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
		for (int i = 0; i < OriginalMj.length; i++) {
			if (OriginalMj[i] == 255) {
				return 0;
			}
		}
		//手中的牌放到list当中
		List<Integer> paiList=new ArrayList<Integer>();
	 
		for (int i = 0; i < OriginalMj.length; i++) {
			paiList.add(OriginalMj[i]);
		}
		 
		   boolean qiFengQuan=(paiList.contains(31)&&paiList.contains(32)&&paiList.contains(33)&&paiList.contains(34)&&
				   paiList.contains(35)&&paiList.contains(36)&&paiList.contains(37));
		 for(int i=0;i<paiList.size();i++){
			 if(paiList.get(i)==caiShen){
				 paiList.remove(i);
			 }
		 }
		Integer[] mjs = paiList.toArray(new Integer[0]);
		 int[] mjs2 = new int[mjs.length];
		 for(int i=0;i<mjs.length;i++){
		    mjs2[i] = mjs[i];
		 }
		 if(shiSanLanQueYiMen(mjs2)==20){
			 if(qiFengQuan){
				 return 40;
			 }
		 }
		return 0;
	}
	/**
	 * 判断十三烂缺一门
	 * @param byHandMj
	 * @return
	 */
	public static int shiSanLanQueYiMen(int byHandMj[]){
		int wanCount = 0;
		int tongCount = 0;
		int tiaoCount = 0;
		for (int i = 0; i < byHandMj.length; i++) {
			if (IsWan(byHandMj[i])) {
				wanCount++;
			}
			if (IsTong(byHandMj[i])) {
				tongCount++;
			}
			if (IsSuo(byHandMj[i])) {
				tiaoCount++;
			}
		}
		// 缺一门
		if(wanCount == 0 || tongCount == 0 || tiaoCount == 0)
			return 20;
		// 缺两门
		 
		return 0;
	}
	public static boolean shiSanLan(int OriginalMj[]) {
		
		// 建立list用于放万牌
		List<Integer> wanList = new ArrayList<Integer>();
		// 建立list用于放条牌
		List<Integer> tiaoList = new ArrayList<Integer>();
		// 建立list用于放筒牌
		List<Integer> tongList = new ArrayList<Integer>();

		for (int i = 0; i <= OriginalMj.length - 2; i++) {
			if(OriginalMj[i]==OriginalMj[i+1]){
				return false;
			}
			 
			if (IsWan(OriginalMj[i])) {
				wanList.add(OriginalMj[i]);
				if (OriginalMj[i] == 9) {

				} else {
					if (OriginalMj[i] + 1 == OriginalMj[i + 1]
							|| OriginalMj[i] + 2 == OriginalMj[i + 1]) {
						return false;
					}
				}
			}
			if (IsSuo(OriginalMj[i])) {
				tiaoList.add(OriginalMj[i]);
				if (OriginalMj[i] == 29) {

				} else {
					if (OriginalMj[i] + 1 == OriginalMj[i + 1]
							|| OriginalMj[i] + 2 == OriginalMj[i + 1]) {
						return false;
					}
				}
			}
			if (IsTong(OriginalMj[i])) {
				tongList.add(OriginalMj[i]);
				if (OriginalMj[i] == 19) {

				} else {
					if (OriginalMj[i] + 1 == OriginalMj[i + 1]
							|| OriginalMj[i] + 2 == OriginalMj[i + 1]) {
						return false;
					}
				}
			}
		}

		return true;
	}

	/**
	 * 判断是否宝归位
	 * 
	 * @param byHandMj
	 * @param byMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static int findRandMjNoInHand(int byHandMj[], int cs) {
		for (int i = 0; i < m_testMjPai.length; i++) {
			boolean found = false;
			for (int k = 0; k < byHandMj.length; k++) {
				if (m_testMjPai[i] == byHandMj[k] || m_testMjPai[i] == cs
						|| Math.abs(m_testMjPai[i] - byHandMj[k]) <= 1) {
					found = true;
					break;
				}
			}
			if (found) {
				continue;
			} else {
				return m_testMjPai[i];
			}
		}
		return 0;
	}

	/**
	 * 红中替宝是否可以胡
	 * 
	 * @param byHandMj
	 * @param hu
	 * @param caiShen
	 * @param bZiMo
	 * @param list
	 * @return
	 */
	public static boolean HongZongTibaoHu(int byHandMj[], int byMj, HU hu,
			int caiShen, boolean bZiMo, ArrayList<HU> list) {

		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
			byMj = Constants.INVALID_CARD;
		}
		SortCard(OriginalMj, Constants.HAND_MJ_MAX);

		// 七小对胡
		int retType = TDHHelper.IsPaiXinQiDuiZi(byHandMj, hu, byMj, caiShen,
				bZiMo);
		if (retType != 0) {
			MajTable.hu_Type = Constants.HU_TYPE_QIDUI;
			return true;
		}
		// 十三烂胡
		int shiSanLanHu = IsShiSanLan(OriginalMj, byMj, hu, caiShen, bZiMo,
				list);
		if (shiSanLanHu > 0) {
			return true;
		}
		// 遍历手中的牌
		int countHongZhong = Constants.countof(OriginalMj, 35);
		if (countHongZhong == 0) {

			return IsHu(OriginalMj, byMj, hu, caiShen, bZiMo, list);
		}

		// countHongZhong>=1
		// baoPai变成手中没有牌
		int baoPai = 2;
		int mumber = 0;
		for (int i = 0; i < m_testMjPai.length; i++) {
			for (int j = 0; j < OriginalMj.length; j++) {
				if (m_testMjPai[i] == OriginalMj[j]
						|| m_testMjPai[i] == caiShen) {
					mumber++;
					break;
				}
			}
			if (mumber == 0) {
				baoPai = m_testMjPai[i];
				break;
			} else {
				mumber = 0;
			}
		}

		if (Constants.countof(OriginalMj, caiShen) == 0) {
			for (int i = 0; i < OriginalMj.length; i++) {
				if (OriginalMj[i] == caiShen) {
					OriginalMj[i] = baoPai;
				}
			}
			for (int i = 0; i < OriginalMj.length; i++) {
				if (OriginalMj[i] == 35) {
					OriginalMj[i] = caiShen;
				}
			}

			return IsHu(OriginalMj, (byMj == 35) ? caiShen : byMj, hu, baoPai,
					bZiMo, list);
		} else {
			for (int i = 0; i < OriginalMj.length; i++) {
				if (OriginalMj[i] == caiShen) {
					OriginalMj[i] = baoPai;
				}
			}
			for (int i = 0; i < OriginalMj.length; i++) {
				if (OriginalMj[i] == 35) {
					OriginalMj[i] = caiShen;
				}
			}
			return IsHu(OriginalMj, 255, hu, baoPai, bZiMo, list);
		}
	}

	public static boolean IsHu(int byHandMj[], int byMj, HU hu, int caiShen,
			boolean bZiMo, ArrayList<HU> list) {
		// if(bZiMo == false) return false;
		// 排序牌面
		// 宝归位
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
			byMj = Constants.INVALID_CARD;
		}
		// 四个宝牌必须胡牌
		if (Constants.countof(OriginalMj, caiShen) == 4) {
			return true;
		}
		SortCard(OriginalMj, Constants.HAND_MJ_MAX);
		MajHelper.AnalyseBlock(byHandMj, byMj, hu, caiShen, list);

		if (IsHuCS2(byHandMj, byMj, hu, caiShen, bZiMo, list)) {
			if (IsAllowHuCS2(byHandMj, byMj, hu, caiShen, bZiMo, list)) {
				MajTable.hu_Type = Constants.HU_TYPE_COMMON;
				return true;
			}
		}

		/*
		 * if (caiShen != Constants.INVALID_CARD) { if (caishenNum > 0) {
		 * 
		 * } else { int baiNum = 0; int[] OriginalMj1 = OriginalMj.clone(); for
		 * (int i = 0; i < OriginalMj1.length; i++) { int j = OriginalMj1[i]; if
		 * (j == Constants.bai) { OriginalMj1[i] = caiShen; baiNum++; } } if
		 * (baiNum > 0 && IsHu(OriginalMj1, byMj, hu, tempHu,
		 * Constants.INVALID_CARD)) { return true; } } }
		 */

		// 无财神情况
		return false;
	}

	public static boolean IsAllowHuCS2(int byHandMj[], int byMj, HU hu,
			int caishen, boolean bZiMo, ArrayList<HU> list) {
		/*
		 * if (bZiMo == true) {
		 * 
		 * 
		 * return true; } return false;
		 */
		return true;
	}

	public static boolean IsHuCS2(int byHandMj[], int byMj, HU hu, int caishen,
			boolean bZiMo, ArrayList<HU> list) {

		int test_mj[] = new int[Constants.HAND_MJ_MAX];
		int cntCS = 0;
		if (caishen == Constants.INVALID_CARD) {
			cntCS = 0;
		} else {
			cntCS = Constants.countof(byHandMj, caishen,
					Constants.HAND_MJ_MAX);
		}

		if (bZiMo) {
			if (byMj == caishen) {
				cntCS++;
			}
		}

		for (int i = 0; i < list.size(); i++) {

			HU out_hu = list.get(i);
			for (int j = 0; j < (Constants.HAND_MJ_MAX - 2) / 3; j++) {

			}
			// 取出胡牌的类型

			int cntBlock = 0;
			for (int j = 0; j < (Constants.HAND_MJ_MAX - 2) / 3; j++) {
				if (hu.block[j].style != Constants.BLOCK_NULL) {
					cntBlock++;
				}
				if (out_hu.block[j].style != Constants.BLOCK_NULL) {
					cntBlock++;
				}
			}
			if (cntBlock == Constants.MAX_BLOCK_NUM
					&& out_hu.jiangMj != Constants.INVALID_CARD) {
				MajTable.hu_Index = i;
				MajHelper.hu_Index = i;
				return true;
			}
			if (out_hu.sanMj[0] == Constants.INVALID_CARD) {
				MajTable.hu_Index = i;
				MajHelper.hu_Index = i;
				return true;
			}
			if (out_hu.sanMj[1] == Constants.INVALID_CARD) {
				if (out_hu.jiangMj == Constants.INVALID_CARD) {
					if (cntCS == 1) {
						MajTable.hu_Index = i;
						MajHelper.hu_Index = i;
						return true;
					}
				} else {
					MajTable.hu_Index = i;
					MajHelper.hu_Index = i;
					return true;
				}
			}

			if (out_hu.jiangMj != Constants.INVALID_CARD) {

				int need_cs = 0;
				Constants.memset(test_mj, Constants.INVALID_CARD,
						Constants.HAND_MJ_MAX);
				Constants.memcpy(test_mj, out_hu.sanMj, Constants.HAND_MJ_MAX);

				int cntTmpBlock = cntBlock;

				SortCard(test_mj, (int) Constants.HAND_MJ_MAX);

				for (int j = 0; j < Constants.HAND_MJ_MAX - 1; j++) {
					if (test_mj[j] == Constants.INVALID_CARD) {
						break;
					}
					if (IsKaoPai(test_mj[j], test_mj[j + 1])) {
						cntTmpBlock++;
						need_cs++;
						j += 1;
					} else {
						cntTmpBlock++;
						need_cs += 2;
					}
				}

				if (cntTmpBlock == 4 && need_cs <= cntCS) {
					MajTable.hu_Index = i;
					MajHelper.hu_Index = i;
					return true;
				}
			} else {

				int jiangMj = Constants.INVALID_CARD;
				for (int k = 0; k < Constants.HAND_MJ_MAX; k++) {
					int cntTmpBlock = cntBlock;
					jiangMj = Constants.INVALID_CARD;
					int need_cs = 0;
					Constants.memset(test_mj, Constants.INVALID_CARD,
							Constants.HAND_MJ_MAX);
					Constants.memcpy(test_mj, out_hu.sanMj,
							Constants.HAND_MJ_MAX);
					if (test_mj[k] != Constants.INVALID_CARD) {

						if (out_hu.jiangMj == Constants.INVALID_CARD) {
							if (k + 1 < Constants.HAND_MJ_MAX
									&& test_mj[k] == test_mj[k + 1]) {
								jiangMj = test_mj[k];
								test_mj[k] = Constants.INVALID_CARD;
								test_mj[k + 1] = Constants.INVALID_CARD;

							} else {
								jiangMj = test_mj[k];
								test_mj[k] = Constants.INVALID_CARD;
								need_cs++;
							}

						} else {
							jiangMj = out_hu.jiangMj;
						}
						SortCard(test_mj, (int) Constants.HAND_MJ_MAX);

						for (int j = 0; j < Constants.HAND_MJ_MAX - 1; j++) {
							if (test_mj[j] == Constants.INVALID_CARD) {
								break;
							}
							if (IsKaoPai(test_mj[j], test_mj[j + 1])) {
								cntTmpBlock++;
								need_cs++;
								j += 1;
							} else {
								cntTmpBlock++;
								need_cs += 2;
							}
						}
					} else {
						jiangMj = out_hu.jiangMj;
					}
					if (cntTmpBlock == 4 && need_cs <= cntCS) {
						if (jiangMj != Constants.INVALID_CARD) {
							MajTable.hu_Index = i;
							MajHelper.hu_Index = i;
							return true;

						}
						if (test_mj[1] == Constants.INVALID_CARD) {
							if (cntCS == 1) {
								MajTable.hu_Index = i;
								MajHelper.hu_Index = i;
								return true;
							}
						}
						if (test_mj[2] == Constants.INVALID_CARD) {
							if (cntCS == 3) {
								MajTable.hu_Index = i;
								MajHelper.hu_Index = i;
								return true;
							}
						}
						if (cntCS - need_cs == 2) {
							MajTable.hu_Index = i;
							MajHelper.hu_Index = i;
							return true;
						}

					}
				}
			}
		}
		return false;
	}

	public static int GetUseBaoNum(HU hu) {
		int num = 0;
		for (int i = 0; i < hu.block.length; i++) {
			BLOCK block = hu.block[i];
			if (block.first == 0)
				num++;
		}
		return num;
	}

	// 把散牌处理成值加个数
	public static ArrayList<SanMj> RemoveToDanZhang(int[] sans) {
		ArrayList<SanMj> dz = new ArrayList<SanMj>();
		for (int i = 0; i < sans.length - 1; i++) {
			if (sans[i] == 255)
				return dz;
			SanMj mj = new SanMj(sans[i], 1);
			while (i <= sans.length - 1 && sans[i + 1] == sans[i]) {
				mj.m_num++;
				i++;
			}
			dz.add(mj);
		}
		return dz;
	}

	// 拿到可能是将牌的值
	public static int GetAlikeJiang(ArrayList<SanMj> mjs) {
		if (mjs.size() == 1 && mjs.get(0).m_num == 2)
			return mjs.get(0).m_mj;
		// 先找分散的 56 88
		for (int i = 0; i < mjs.size(); i++) {
			if (mjs.get(i).m_num == 2) {
				if (i < mjs.size() - 1
						&& Math.abs(mjs.get(i + 1).m_mj - mjs.get(i).m_mj) > 1) {
					return mjs.get(i).m_mj;
				}
				if (i == mjs.size() - 1) {
					return mjs.get(i).m_mj;
				}
			}
		}
		// 可能都连着呢比如556677 包牌是44,从后往前找
		for (int i = mjs.size() - 1; i >= 0; i--) {
			if (mjs.get(i).m_num == 2) {
				return mjs.get(i).m_mj;
			}
		}
		return 0;
	}

	// 拿掉散牌中可能是将的,不连续的就是,2张一样的
	public static void RemoveAlikeJiang(ArrayList<SanMj> mjs) {
		if (mjs.size() == 1) {
			if (mjs.get(0).m_num == 1) {
				// 肯定是将
				mjs.remove(0);
			}
			return;
		}
		// 先找分散的 56 88
		for (int i = 0; i < mjs.size(); i++) {
			if (mjs.get(i).m_num == 2) {
				if (i < mjs.size() - 1
						&& Math.abs(mjs.get(i + 1).m_mj - mjs.get(i).m_mj) > 1) {
					mjs.remove(i);
					return;
				}
				if (i == mjs.size() - 1) {
					mjs.remove(i);
					return;
				}
			}
		}
		// 可能都连着呢比如556677 包牌是44,从后往前找
		for (int i = mjs.size() - 1; i >= 0; i--) {
			if (mjs.get(i).m_num == 2) {
				mjs.remove(i);
				return;
			}
		}
	}

	public static boolean IsShunZiNoSort(int mj1, int mj2, int mj3) {
		List<Integer> sorts = new ArrayList<Integer>();
		sorts.add(mj1);
		sorts.add(mj2);
		sorts.add(mj3);
		Collections.sort(sorts);
		if (sorts.get(0) == sorts.get(1) - 1
				&& sorts.get(1) == sorts.get(2) - 1)
			return true;
		else
			return false;
	}
	
	// 处理所有可能的顺子
	public static ArrayList<BLOCK> ChangeToBaoPaiShunZiAny(
			ArrayList<SanMj> mjs, int cs) {
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		if (mjs.size() == 1) {
			// 这种情况一定是两种宝牌做成一个顺子了
			if (mjs.get(0).m_num == 1) {
				if (mjs.get(0).m_mj > 29) {
					// 是风牌啥也不做
				} else if (Math.abs(cs - mjs.get(0).m_mj) <= 2) {
					// 宝牌可以归位
					BLOCK block1 = new BLOCK();
					block1.first = mjs.get(0).m_mj - 2;
					block1.style = 2;
					blocks.add(block1);
					
					BLOCK block2 = new BLOCK();
					block2.first = mjs.get(0).m_mj - 1;
					block2.style = 2;
					blocks.add(block2);
					
					BLOCK block3 = new BLOCK();
					block3.first = mjs.get(0).m_mj;
					block3.style = 2;
					blocks.add(block3);
				} else {
					// 宝牌无法归位
					int mj = mjs.get(0).m_mj;
					if (mj % 10 == 1) {
						// 1,2,3,11,12,13,21,22,23
						BLOCK block = new BLOCK();
						block.first = mj;
						block.style = 2;
						blocks.add(block);
					} else if (mj % 10 == 9) {
						// 7,8,9...
						BLOCK block = new BLOCK();
						block.first = mj - 2;
						block.style = 2;
						blocks.add(block);
					} else {
						BLOCK block = new BLOCK();
						block.first = mj - 1;
						block.style = 2;
						blocks.add(block);
					}
				}
			} else if (mjs.get(0).m_num == 2) {
				// 跟宝牌组成一个刻子，啥也不做
			}
		}
		for (int i = 0; i < mjs.size() - 1; i++) {
			if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 1) {
				if (IsShunZiNoSort(cs, mjs.get(i).m_mj, mjs.get(i + 1).m_mj)) {
					int before = mjs.get(i).m_mj - 1;
					if (IsWST(before)) {
						BLOCK block = new BLOCK();
						block.first = before;
						block.style = 2;
						blocks.add(block);
					}
					int after = mjs.get(i + 1).m_mj + 1;
					if (IsWST(after)) {
						BLOCK block = new BLOCK();
						block.first = mjs.get(i).m_mj;
						block.style = 2;
						blocks.add(block);
					}
					i += 1;
				}
			} else if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 2) {
				for (int k = 0; k < mjs.get(i).m_num; k++) {
					BLOCK block = new BLOCK();
					block.first = mjs.get(i).m_mj;
					block.style = 2;
					blocks.add(block);
				}
				i += 1;
			}
		}
		return blocks;
	}
	public static ArrayList<BLOCK> ChangeToBaoPaiDuZi(ArrayList<SanMj> mjs,int cs){
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		if(mjs.size() == 1){
		}else if(mjs.size() == 2 || mjs.size() == 4 || mjs.size() == 6){
			for(int i = 0;i < mjs.size();i += 2){
				int mj1 = mjs.get(i).m_mj;
				int mj2 = mjs.get(i + 1).m_mj;
				if(Math.abs(mj2 - mj1) == 2 || mj1 % 10 == 1 || mj2 % 10 == 9){
					for (int k = 0; k < mjs.get(i).m_num; k++) {
						BLOCK block = new BLOCK();
						block.first = mjs.get(i).m_mj;
						block.style = 2;
						blocks.add(block);
					}
				}
			}
		}
		
		return blocks;
	}
	//返回需要的包牌个数
	public static int ChangeToBaoPaiNum(ArrayList<SanMj> mjs,int cs,boolean hasJiang,int byMj){
		int csNeed = 0;
		if(mjs.size() == 1){
			if(mjs.get(0).m_num == 1){
				//一定是需要2个宝牌配成顺子
				if(!hasJiang){
					if(byMj == mjs.get(0).m_mj)
						csNeed += 0;
					else
						csNeed += 2;
				}
			}else if(mjs.get(0).m_num == 2){
				//跟一个包牌组成刻子
				if(!hasJiang)
					csNeed += 1;
			}
		}else if(mjs.size() == 2){
			int mj1 = mjs.get(0).m_mj;
			int mj2 = mjs.get(1).m_mj;
			if(Math.abs(mj1 - mj2) <= 2 && mjs.get(0).m_num == mjs.get(0).m_num){
				csNeed += mjs.get(0).m_num;
			}else{
				if(mjs.get(0).m_num == 1){
					//一定是需要2个宝牌配成顺子
					if(!hasJiang){
						if(byMj == mjs.get(0).m_mj)
							csNeed += 0;
						else
							csNeed += 2;
					}
				}else if(mjs.get(0).m_num == 2){
					//跟一个包牌组成刻子
					if(!hasJiang)
						csNeed += 1;
				}	
				
				if(mjs.get(1).m_num == 1){
					//一定是需要2个宝牌配成顺子
					if(!hasJiang){
						if(byMj == mjs.get(1).m_mj)
							csNeed += 0;
						else
							csNeed += 2;
					}
				}else if(mjs.get(1).m_num == 2){
					//跟一个包牌组成刻子
					if(!hasJiang)
						csNeed += 1;
				}
			}
		}else{
			for(int i = 0;i < mjs.size();){
				int mj1 = mjs.get(i).m_mj;
				if((i + 1) < mjs.size()){
					int mj2 = mjs.get(i + 1).m_mj;
					if(Math.abs(mj2 - mj1) <= 2){
						csNeed += mjs.get(i).m_num;
						i+=2;
					}else{
						if(mjs.get(i).m_num == 1){
							//一定是需要2个宝牌配成顺子
							if(hasJiang){
								if(mj1 == byMj)
									csNeed += 0;
								else
									csNeed += 1;
								hasJiang = false;
							}
						}else if(mjs.get(i).m_num == 2){
							//跟一个宝牌组成刻子
							csNeed += 1;
						}
						i+=1;
					}
				}else{
					if(mjs.get(i).m_num == 1){
						//一定是需要2个宝牌配成顺子
						if(!hasJiang){
							if(byMj == mjs.get(i).m_mj)
								csNeed += 0;
							else
								csNeed += 2;
						}
					}else if(mjs.get(i).m_num == 2){
						//跟一个包牌组成刻子
						if(!hasJiang)
							csNeed += 1;
					}	
					i+=1;
				}
			}
		}
		
		return csNeed;
	}
	// 顺子刻子
	public static ArrayList<BLOCK> ChangeToBaoPaiShunZiKeZi(
			ArrayList<SanMj> mjs, int cs) {
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		if (mjs.size() == 1) {
			// 这种情况一定是两种宝牌做成一个顺子了
			if (mjs.get(0).m_num == 1) {
				if (mjs.get(0).m_mj > 29) {
					// 是风牌啥也不做
				} else if (Math.abs(cs - mjs.get(0).m_mj) <= 2) {
					// 宝牌可以归位
					BLOCK block = new BLOCK();
					block.first = Math.min(cs, mjs.get(0).m_mj);
					block.style = 2;
					blocks.add(block);
				} else {
					// 宝牌无法归位
					int mj = mjs.get(0).m_mj;
					if (mj % 10 == 1) {
						// 1,2,3,11,12,13,21,22,23
						BLOCK block = new BLOCK();
						block.first = mj;
						block.origValue = mj;
						block.style = 2;
						blocks.add(block);
					} else if (mj % 10 == 9) {
						// 7,8,9...
						BLOCK block = new BLOCK();
						block.first = mj - 2;
						block.origValue = mj;
						block.style = 2;
						blocks.add(block);
					} else if (mj == cs) {
						// 红中替宝，优先处理成刻子
						BLOCK block = new BLOCK();
						block.first = mj;
						block.style = 4;
						block.origValue = mj;
						blocks.add(block);
					} else {
						BLOCK block = new BLOCK();
						block.first = mj - 1;
						block.style = 2;
						block.origValue = mj;
						blocks.add(block);
					}
				}
			} else if (mjs.get(0).m_num == 2) {
				// 跟宝牌组成一个刻子
				BLOCK block = new BLOCK();
				block.first = mjs.get(0).m_mj;
				block.style = 4;
				block.origValue = mjs.get(0).m_mj;
				blocks.add(block);
			}
		}
		for (int i = 0; i < mjs.size() - 1; i++) {
			if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 1) {
				if (IsShunZiNoSort(cs, mjs.get(i).m_mj, mjs.get(i + 1).m_mj)) {
					for (int k = 0; k < mjs.get(i).m_num; k++) {
						BLOCK block = new BLOCK();
						block.first = Math.min(cs,
								Math.min(mjs.get(i).m_mj, mjs.get(i + 1).m_mj));
						block.style = 2;
						block.origValue = mjs.get(i).m_mj;
						blocks.add(block);
					}
					i += 1;
				}
			} else if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 2) {
				for (int k = 0; k < mjs.get(i).m_num; k++) {
					BLOCK block = new BLOCK();
					block.first = mjs.get(i).m_mj;
					block.style = 2;
					block.origValue = mjs.get(i).m_mj;
					blocks.add(block);
				}
				i += 1;
			} else if (mjs.get(i).m_num == 2) {
				BLOCK block = new BLOCK();
				block.first = mjs.get(i).m_mj;
				block.style = 4;
				block.origValue = mjs.get(i).m_mj;
				blocks.add(block);
			}
		}
		return blocks;
	}

	// 只处理顺子
	public static ArrayList<BLOCK> ChangeToBaoPaiShunZi(ArrayList<SanMj> mjs,
			int cs) {
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		if (mjs.size() == 1) {
			// 这种情况一定是两种宝牌做成一个顺子了
			if (mjs.get(0).m_num == 1) {
				if (mjs.get(0).m_mj > 29) {
					// 是风牌啥也不做
				} else if (Math.abs(cs - mjs.get(0).m_mj) <= 2) {
					// 宝牌可以归位
					BLOCK block1 = new BLOCK();
					block1.first = mjs.get(0).m_mj - 2;
					block1.style = 2;
					blocks.add(block1);
					
					BLOCK block2 = new BLOCK();
					block2.first = mjs.get(0).m_mj - 1;
					block2.style = 2;
					blocks.add(block2);
					
					BLOCK block3 = new BLOCK();
					block3.first = mjs.get(0).m_mj;
					block3.style = 2;
					blocks.add(block3);
				} else {
					// 宝牌无法归位
					int mj = mjs.get(0).m_mj;
					if (mj % 10 == 1) {
						// 1,2,3,11,12,13,21,22,23
						BLOCK block = new BLOCK();
						block.first = mj;
						block.style = 2;
						blocks.add(block);
					} else if (mj % 10 == 9) {
						// 7,8,9...
						BLOCK block = new BLOCK();
						block.first = mj - 2;
						block.style = 2;
						blocks.add(block);
					} else {
						BLOCK block = new BLOCK();
						block.first = mj - 1;
						block.style = 2;
						blocks.add(block);
					}
				}
			} else if (mjs.get(0).m_num == 2) {
				// 跟宝牌组成一个刻字，啥也不做
			}
		}
		for (int i = 0; i < mjs.size() - 1; i++) {
			if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 1) {
				if (IsShunZiNoSort(cs, mjs.get(i).m_mj, mjs.get(i + 1).m_mj)) {
					for (int k = 0; k < mjs.get(i).m_num; k++) {
						BLOCK block = new BLOCK();
						block.first = Math.min(cs,
								Math.min(mjs.get(i).m_mj, mjs.get(i + 1).m_mj));
						block.style = 2;
						blocks.add(block);
					}
					i += 1;
				}
			} else if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 2) {
				for (int k = 0; k < mjs.get(i).m_num; k++) {
					BLOCK block = new BLOCK();
					block.first = mjs.get(i).m_mj;
					block.style = 2;
					blocks.add(block);
				}
				i += 1;
			}
		}
		return blocks;
	}

	// 只处理包归位
	public static ArrayList<BLOCK> ChangeToBaoPaiShunZiBGW(
			ArrayList<SanMj> mjs, int cs) {
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		for (int i = 0; i < mjs.size() - 1; i++) {
			if (mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 1
					|| mjs.get(i).m_mj == mjs.get(i + 1).m_mj - 2) {
				if (IsShunZiNoSort(cs, mjs.get(i).m_mj, mjs.get(i + 1).m_mj)) {
					for (int k = 0; k < mjs.get(i).m_num; k++) {
						BLOCK block = new BLOCK();
						block.first = Math.min(cs,
								Math.min(mjs.get(i).m_mj, mjs.get(i + 1).m_mj));
						block.style = 2;
						blocks.add(block);
					}
					i += 1;
				}
			}
		}
		return blocks;
	}

	public static int GetBanBanGaoNum(HU hu, int cs) {
		ArrayList<BLOCK> blocks = new ArrayList<BLOCK>();
		for (int i = 0; i < 4; i++) {
			BLOCK block = hu.block[i];
			if (block.first != 0 && block.style == 2) {
				blocks.add(block);
			}
		}
		ArrayList<SanMj> dzmj = RemoveToDanZhang(hu.sanMj);
		if (hu.jiangMj == 255)
			RemoveAlikeJiang(dzmj);
		ArrayList<BLOCK> sanBlock = ChangeToBaoPaiShunZi(dzmj, cs);
		for (int i = 0; i < sanBlock.size(); i++) {
			blocks.add(sanBlock.get(i));
		}
		Collections.sort(blocks, new Comparator<BLOCK>() {
			public int compare(BLOCK arg0, BLOCK arg1) {
				return arg0.first <= arg1.first ? -1 : 1;
			}
		});
		int bbCount = 0;
		for (int i = 0; i < blocks.size() - 1; i++) {
			if (blocks.get(i).first == blocks.get(i + 1).first) {
				bbCount++;
				i++;
			}
		}
		return bbCount;
	}

	public static int AnalyseBlock(int byHandMj[], int byMj, HU hu,
			int caishen, ArrayList<HU> list) {
		// 排序牌面
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byHandMj, Constants.HAND_MJ_MAX);
		if (byMj != Constants.INVALID_CARD
				&& OriginalMj[Constants.HAND_MJ_MAX - 1] == Constants.INVALID_CARD) {
			OriginalMj[Constants.HAND_MJ_MAX - 1] = byMj;
			byMj = Constants.INVALID_CARD;
		}

		SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);

		Constants.replace(OriginalMj, caishen, Constants.INVALID_CARD);
		// Constants.replace(OriginalMj, bai, caishen);
		SortCard(OriginalMj, Constants.HAND_MJ_MAX);
		int tempMj[] = new int[Constants.HAND_MJ_MAX];
		int tempMj2[] = new int[Constants.HAND_MJ_MAX];
		// 将牌位在整数块( 0, 3, 6, 9, 12, 15 )处
		// 设置变量
		MJ_BLOCK block0 = null;
		MJ_BLOCK block1 = null;
		MJ_BLOCK block2 = null;
		// if( IsJiang( tempMj[i], tempMj[i+1] ) )
		{
			// 胡牌结构处理

			for (int i = 0; i < Constants.HAND_MJ_MAX - 1; i++) {
				Constants.memcpy(tempMj, OriginalMj, Constants.HAND_MJ_MAX);
				HU out_hu = new HU();

				if (IsJiang(tempMj[i], tempMj[i + 1])) {
					out_hu.jiangMj = tempMj[i];
					tempMj[i] = Constants.INVALID_CARD;
					tempMj[i + 1] = Constants.INVALID_CARD;
				}
				Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
				SortCard(tempMj2, Constants.HAND_MJ_MAX);

				DG_HU(tempMj2, out_hu, list);
				/*
				 * block0 = hasBlock(tempMj2, tempMj2[j]); block1 =
				 * hasBlock(tempMj2, tempMj2[j+1]); block2 = hasBlock(tempMj2,
				 * tempMj2[j+2]); if (block0.style == Constants.BLOCK_KE) {
				 * 
				 * AddBlock(out_hu, block0); Constants.replace(tempMj2,
				 * block0.first, Constants.INVALID_CARD, 3); SortCard(tempMj2,
				 * Constants.HAND_MJ_MAX); Constants.memcpy(out_hu.sanMj,
				 * tempMj2, Constants.HAND_MJ_MAX); // if (DG_HU(tempMj2, hu,
				 * list)) { // return false; // } ; continue; } else if
				 * (block0.style == Constants.BLOCK_SUN) {
				 * 
				 * AddBlock(out_hu, block0); Constants.replace(tempMj2,
				 * block0.first, Constants.INVALID_CARD, 1);
				 * Constants.replace(tempMj2, block0.first + 1,
				 * Constants.INVALID_CARD, 1); Constants.replace(tempMj2,
				 * block0.first + 2, Constants.INVALID_CARD, 1);
				 * SortCard(tempMj2, Constants.HAND_MJ_MAX);
				 * Constants.memcpy(out_hu.sanMj, tempMj2,
				 * Constants.HAND_MJ_MAX); // if (DG_HU(tempMj2, hu, list)) { //
				 * return false; // } ; continue; } else if (block1.style ==
				 * Constants.BLOCK_SUN) {
				 * 
				 * AddBlock(out_hu, block1); Constants.replace(tempMj2,
				 * block1.first, Constants.INVALID_CARD, 1);
				 * Constants.replace(tempMj2, block1.first + 1,
				 * Constants.INVALID_CARD, 1); Constants.replace(tempMj2,
				 * block1.first + 2, Constants.INVALID_CARD, 1);
				 * SortCard(tempMj2, Constants.HAND_MJ_MAX);
				 * Constants.memcpy(out_hu.sanMj, tempMj2,
				 * Constants.HAND_MJ_MAX); // if (DG_HU(tempMj2, hu, list)) { //
				 * return false; // } ; continue; } else if (block2.style ==
				 * Constants.BLOCK_SUN) {
				 * 
				 * AddBlock(out_hu, block2); Constants.replace(tempMj2,
				 * block2.first, Constants.INVALID_CARD, 1);
				 * Constants.replace(tempMj2, block2.first + 1,
				 * Constants.INVALID_CARD, 1); Constants.replace(tempMj2,
				 * block2.first + 2, Constants.INVALID_CARD, 1);
				 * SortCard(tempMj2, Constants.HAND_MJ_MAX);
				 * Constants.memcpy(out_hu.sanMj, tempMj2,
				 * Constants.HAND_MJ_MAX); // if (DG_HU(tempMj2, hu, list)) { //
				 * return false; // } ; continue; }else{
				 * 
				 * }
				 * 
				 * j++; }
				 */
			}
		}

		return list.size();
	}

	public static MJ_BLOCK hasBlock(int[] byHandMj, int byMj) {
		MJ_BLOCK block = new MJ_BLOCK();

		if (byMj == Constants.INVALID_CARD) {
			for (int j = 0; j < Constants.HAND_MJ_MAX - 2; j++) {
				byMj = byHandMj[j];
				if (byMj != Constants.INVALID_CARD) {
					if (Constants.countof(byHandMj, byMj) >= 3) {
						block.style = Constants.BLOCK_KE;
						block.first = byMj;
						return block;
					}
					if (Constants.countof(byHandMj, byMj) >= 1
							&& Constants.countof(byHandMj, byMj + 1) >= 1
							&& Constants.countof(byHandMj, byMj + 2) >= 1
							&& MajHelper.IsTongHuaSe(byMj, byMj + 1, byMj + 2)) {
						block.style = Constants.BLOCK_SUN;
						block.first = byMj;
						return block;
					}
				}
			}
		} else {
			if (Constants.countof(byHandMj, byMj) >= 3) {
				block.style = Constants.BLOCK_KE;
				block.first = byMj;
				return block;
			}
			if (Constants.countof(byHandMj, byMj) >= 1
					&& Constants.countof(byHandMj, byMj + 1) >= 1
					&& Constants.countof(byHandMj, byMj + 2) >= 1
					&& MajHelper.IsTongHuaSe(byMj, byMj + 1, byMj + 2)) {
				block.style = Constants.BLOCK_SUN;
				block.first = byMj;
				return block;
			}
		}

		return block;
	}

	/**
	 * 
	 * @param byMj1
	 * @param byMj2
	 * @return
	 */
	public static boolean IsKaoPai(int byMj1, int byMj2) {
		if (((byMj1 == byMj2) || (byMj1 + 1 == byMj2) || (byMj1 + 2 == byMj2))
				&& MajHelper.IsTongHuaSe(byMj1, byMj2)) {
			return true;
		}
		return false;
	}

	public static boolean DG_HU(int tempMj[], HU out_hu, ArrayList<HU> list) {

		int tempMj2[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
		MJ_BLOCK block0 = null;
		MJ_BLOCK block1 = null;
		MJ_BLOCK block2 = null;

		for (int c0 = 0; c0 < Constants.HAND_MJ_MAX - 2; c0++) {
			if (tempMj2[c0] == Constants.INVALID_CARD) {
				break;
			}
			block0 = hasBlock(tempMj2, tempMj2[c0]);
			if (IsTongHuaSe(tempMj2[c0], tempMj2[c0 + 1])) {
				block1 = hasBlock(tempMj2, tempMj2[c0 + 1]);
			} else {
				block1 = null;
			}
			if (IsTongHuaSe(tempMj2[c0], tempMj2[c0 + 2])) {
				block2 = hasBlock(tempMj2, tempMj2[c0 + 2]);
			} else {
				block2 = null;
			}

			Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
			if (block0.style == Constants.BLOCK_KE) {

				AddBlock(out_hu, block0);
				Constants.replace(tempMj2, block0.first,
						Constants.INVALID_CARD, 3);
				SortCard(tempMj2, Constants.HAND_MJ_MAX);
				Constants.memcpy(out_hu.sanMj, tempMj2, Constants.HAND_MJ_MAX);
				DG_HU(tempMj2, out_hu, list);
				out_hu.removeLastBlock();
			}
			Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
			if (block0.style == Constants.BLOCK_SUN) {

				AddBlock(out_hu, block0);
				Constants.replace(tempMj2, block0.first,
						Constants.INVALID_CARD, 1);
				Constants.replace(tempMj2, block0.first + 1,
						Constants.INVALID_CARD, 1);
				Constants.replace(tempMj2, block0.first + 2,
						Constants.INVALID_CARD, 1);
				SortCard(tempMj2, Constants.HAND_MJ_MAX);
				Constants.memcpy(out_hu.sanMj, tempMj2, Constants.HAND_MJ_MAX);
				DG_HU(tempMj2, out_hu, list);
				out_hu.removeLastBlock();
			}
			Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
			if (block1 != null && block1.style == Constants.BLOCK_SUN) {

				AddBlock(out_hu, block1);
				Constants.replace(tempMj2, block1.first,
						Constants.INVALID_CARD, 1);
				Constants.replace(tempMj2, block1.first + 1,
						Constants.INVALID_CARD, 1);
				Constants.replace(tempMj2, block1.first + 2,
						Constants.INVALID_CARD, 1);
				SortCard(tempMj2, Constants.HAND_MJ_MAX);
				Constants.memcpy(out_hu.sanMj, tempMj2, Constants.HAND_MJ_MAX);
				DG_HU(tempMj2, out_hu, list);
				out_hu.removeLastBlock();
			}
			Constants.memcpy(tempMj2, tempMj, Constants.HAND_MJ_MAX);
			if (block2 != null && block2.style == Constants.BLOCK_SUN) {

				AddBlock(out_hu, block2);
				Constants.replace(tempMj2, block2.first,
						Constants.INVALID_CARD, 1);
				Constants.replace(tempMj2, block2.first + 1,
						Constants.INVALID_CARD, 1);
				Constants.replace(tempMj2, block2.first + 2,
						Constants.INVALID_CARD, 1);
				SortCard(tempMj2, Constants.HAND_MJ_MAX);
				Constants.memcpy(out_hu.sanMj, tempMj2, Constants.HAND_MJ_MAX);
				DG_HU(tempMj2, out_hu, list);
				out_hu.removeLastBlock();
			}

		}
		int isHasBlock = 0;
		for (int c0 = 0; c0 < Constants.HAND_MJ_MAX - 2; c0++) {
			if (tempMj2[c0] == Constants.INVALID_CARD)
				break;
			block0 = hasBlock(tempMj2, tempMj2[c0]);
			block1 = hasBlock(tempMj2, tempMj2[c0 + 1]);
			block2 = hasBlock(tempMj2, tempMj2[c0 + 2]);
			if (block0.style == Constants.BLOCK_KE) {
				isHasBlock++;
			}
			if (block0.style == Constants.BLOCK_SUN) {
				isHasBlock++;
			}
			if (block1.style == Constants.BLOCK_SUN) {
				isHasBlock++;
			}
			if (block2.style == Constants.BLOCK_SUN) {
				isHasBlock++;
			}
		}
		if (isHasBlock == 0) {
			boolean bHasHu = false;

			for (int k = 0; k < list.size(); k++) {
				int cntDY = 0;
				HU tmp_hu_s = list.get(k);
				if (out_hu.jiangMj == tmp_hu_s.jiangMj) {

					for (int m = 0; m < 4; m++) {
						if ((out_hu.block[m].style == tmp_hu_s.block[m].style)
								&& (out_hu.block[m].first == tmp_hu_s.block[m].first)) {
							cntDY++;
						}
					}
					if (cntDY == 4) {
						bHasHu = true;
					}
				}
			}
			if (bHasHu == false) {
				Constants.memcpy(out_hu.sanMj, tempMj2, Constants.HAND_MJ_MAX);
				HU result_hu = new HU();
				result_hu.jiangMj = out_hu.jiangMj;
				for (int j = 0; j < Constants.MAX_BLOCK_NUM; j++) {
					result_hu.block[j].style = out_hu.block[j].style;
					result_hu.block[j].first = out_hu.block[j].first;
				}
				Constants.memcpy(result_hu.sanMj, out_hu.sanMj,
						Constants.HAND_MJ_MAX);
				if (result_hu.jiangMj == Constants.INVALID_CARD) {
					if (result_hu.sanMj[2] == Constants.INVALID_CARD) {
						if (result_hu.sanMj[0] != Constants.INVALID_CARD
								&& result_hu.sanMj[0] == result_hu.sanMj[1]) {
							result_hu.jiangMj = result_hu.sanMj[0];
							result_hu.sanMj[0] = Constants.INVALID_CARD;
							result_hu.sanMj[1] = Constants.INVALID_CARD;
						}
					}
				}
				list.add(result_hu);

			}
		}
		return false;
	}

	public static int bai = 37;

	public static boolean equalsWithCaiShen(int byMj1, int byMj2, int caiShen[]) {
		if (byMj1 == byMj2) {
			return true;
		}
		/*
		 * else{ if (byMj1 == bai || byMj2 == bai) { return true; } }
		 */
		return false;
	}

	public static boolean Test() {

		int test1[][] = new int[][] { { 15, 16, 17, 18, 20, 21, 30, 255, 255,
				255, 255, 255, 255, 255 } };

		int test2[] = { 5, 5, 7, 11, 12, 13, 23, 24, 25, 33, 255, 255, 255,
				255, 255, 255 };

		for (int i = 0; i < 15; i++) {
			HU hu = new HU();
			hu.block[0].style = Constants.BLOCK_PENG;
			// hu.block[1].style = Constants.BLOCK_PENG;
			// hu.block[2].style = Constants.BLOCK_PENG;
			HU out_hu = new HU();
			int caishen = 5;
			ArrayList<HU> list = new ArrayList<HU>();
			// MajHelper.AnalyseBlock(test2, 22, hu, caishen, list);
			// if (IsHu(test2, bai, hu, caishen, true, list)) {
			// if (JHMJHelper.IsPaiXinBaoTou(test2, hu, bai, caishen, list)) {
			// System.out.println("BAO_TOU : " + i);
			// }
			//
			// int retType = JHMJHelper.IsPaiXinShiSanBuKao(test2, 13, caishen);
			// {
			// System.out.println("IsPaiXinShiSanBuKao : " + retType);
			// }
			// System.out.println("OK : " + i);
			// }
		}
		/*
		 * int all[] = new int[]{100,1,2,3,4,5,6,0};
		 * 
		 * for (int i = all.length-1; i > 0; i--) { all[i] = all[i-1]; } all[0]
		 * = -1;
		 */
		class Hand {
			int handMjs[];
			int caiShen;
			boolean isHu;
			int huNum = 0;

			// huNum 自摸每人数量
			// 放统 放统人数量 其他/2
			public Hand(int handMjs[], int caiShen, boolean isHu, int huNum) {
				this.handMjs = handMjs;
				this.caiShen = caiShen;
				this.isHu = isHu;
				this.huNum = huNum;
				run();
			}

			public void run() {
				HU hu = new HU();
				HU out_hu = new HU();
				ArrayList<HU> list = new ArrayList<HU>();
				if (isHu == IsHuCS2(handMjs, 255, hu, caiShen, true, list)) {
					System.out.println("ok");
				} else {
					System.out.println("error");
				}
			}
		}

		new Hand(
				new int[] { 18, 1, 2, 3, 8, 8, 12, 13, 13, 14, 14, 19, 20, 25 },
				25, true, 2);

		new Hand(new int[] { 24, 17, 17, 17, 1, 2, 3, 11, 11, 11, 19, 20, 25,
				26 }, 11, true, 8);// 财神一对头
									// 2番
		// 8

		return true;
	}

	// 去除数组中重复的记录
	public static Integer[] array_unique(int[] a) {
		// array_unique
		List<Integer> list = new LinkedList<Integer>();
		for (int i = 0; i < a.length; i++) {
			if (!list.contains(a[i])) {
				list.add(a[i]);
			}
		}
		return (Integer[]) list.toArray(new Integer[list.size()]);
	}

	public static int[] to_array(Integer[] a) {
		int allMj[] = new int[a.length];
		for (int i = 0; i < a.length; i++) {
			allMj[i] = a[i];
		}
		return allMj;
	}

	public static boolean IsTing(int byHandMj[], int byMj, HU hu,
			int intstMj[], int intstMjCount, int byHuaPai[], int chaiShen) {
		int byHandMjCount = 0;
		for (int byIndex = 0; byIndex < Constants.HAND_MJ_MAX; byIndex++) {
			if (MajHelper.IsWTSZ(byHandMj[byIndex])) {
				byHandMjCount++;
			}
		}
		for (int byIndex = 0; byIndex < Constants.HAND_MJ_MAX; byIndex++) {
			int intmpMj[] = new int[Constants.HAND_MJ_MAX];
			Constants.memcpy(intmpMj, byHandMj, Constants.HAND_MJ_MAX);
			if (((byHandMjCount % 3) == 2) /*
											 * && (byMj ==
											 * Constants.INVALID_CARD)
											 */) {
				intmpMj[byIndex] = Constants.INVALID_CARD;
			}
			if (byIndex != Constants.HAND_MJ_MAX - 1) {
				intmpMj[Constants.HAND_MJ_MAX - 1] = byMj;
			}

			ArrayList<HU> list = new ArrayList<HU>();
			SortCard(intmpMj, Constants.HAND_MJ_MAX);
			for (int i = 0; i < intstMjCount; i++) {
				int intstMjValue = intstMj[i];

				if (IsHu(intmpMj, intstMjValue, hu, chaiShen, true, list)) {
					return true;
				}
			}
		}
		return false;
	}

	public static int GetTingPai(int byHandMj[], HU hu, int byHuaPai[],
			int byResultTingMj[], int chaiShen) {
		int byTingPaiCount = 0;
		int intmpMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(intmpMj, byHandMj, Constants.HAND_MJ_MAX);
		intmpMj[Constants.HAND_MJ_MAX - 1] = Constants.INVALID_CARD;

		SortCard(intmpMj, Constants.HAND_MJ_MAX);

		for (int i = 0; i < 34; i++) {
			int byMj = m_testMjPai[i];
			ArrayList<HU> list = new ArrayList<HU>();
			HU tempHu = new HU();
			CleanHu(tempHu);
			if (IsHu(intmpMj, byMj, hu, chaiShen, false, list)) {
				byResultTingMj[byTingPaiCount++] = byMj;
			}
		}

		return byTingPaiCount;
	}

	public static int GetPaiCount(int byHandMj[]) {
		int cnt = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (byHandMj[i] != Constants.INVALID_CARD) {
				cnt++;
			}
		}
		return cnt;
	}

	public static int GetPaiCount(int byHandMj[], int byMj) {
		int cnt = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (byHandMj[i] == byMj) {
				cnt++;
			}
		}
		return cnt;
	}

	public static int GetChiSelect(int byHandMj[], int byMj, HU tempHu) {
		int byMask = IsChi(byHandMj, byMj);
		int byIndex = 0;
		// 吃牌信息, 0-无吃牌,1-**@型, 2-*@*, 4-@**型
		if (TestBit(byMask, 0)) {
			tempHu.block[byIndex].first = byMj - 2;
			tempHu.block[byIndex].style = Constants.BLOCK_SUN;
			byIndex++;
		}
		if (TestBit(byMask, 1)) {
			tempHu.block[byIndex].first = byMj - 1;
			tempHu.block[byIndex].style = Constants.BLOCK_SUN;
			byIndex++;
		}
		if (TestBit(byMask, 2)) {
			tempHu.block[byIndex].first = byMj;
			tempHu.block[byIndex].style = Constants.BLOCK_SUN;
			byIndex++;
		}
		return byIndex;
	}

	public static boolean TestBit(int var, int bit) {
		return ((var) & (1 << (bit))) != 0;
	}

	// 加入块到胡牌结构
	public static void AddBlock(HU hu, PTR_MJ_BLOCK block) {
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			if (hu.block[i].style == Constants.BLOCK_NULL) {
				hu.block[i].first = block.first;
				hu.block[i].style = block.style;
				hu.block[i].origValue = block.origValue;
				break;
			}
		}
	}

	public static void AddBlock(HU hu, BLOCK block) {
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			if (hu.block[i].style == Constants.BLOCK_NULL) {
				hu.block[i].first = block.first;
				hu.block[i].style = block.style;
				hu.block[i].origValue = block.origValue;
				break;
			}
		}
	}

	public static void AddBlock(HU hu, MJ_BLOCK block) {
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			if (hu.block[i].style == Constants.BLOCK_NULL) {
				hu.block[i].first = block.first;
				hu.block[i].style = block.style;
				hu.block[i].origValue = block.origValue;
				break;
			}
		}
	}

	// 类型判断
	public static MJ_BLOCK CheckBlock(int byMj1, int byMj2, int byMj3) {
		MJ_BLOCK block = new MJ_BLOCK();
		block.first = Constants.INVALID_CARD;
		block.style = Constants.BLOCK_NULL;

		if (byMj1 == Constants.INVALID_CARD || byMj2 == Constants.INVALID_CARD
				|| byMj3 == Constants.INVALID_CARD) {
			return block;
		}
		if (IsTongHuaSe(byMj1, byMj2, byMj3) == false) {
			return block;
		}
		// 如果byMj1, byMj2, byMj3不是顺序结构,排序
		int i, tag, temp;
		for (i = 0, tag = 1; tag == 1 && i < 3; i++) {
			tag = 0;
			if (byMj1 > byMj2) {
				temp = byMj1;
				byMj1 = byMj2;
				byMj2 = temp;
				tag = 1;
			}
			if (byMj2 > byMj3) {
				temp = byMj2;
				byMj2 = byMj3;
				byMj3 = temp;
				tag = 1;
			}
		}

		// 碰形结构
		if (byMj1 == byMj2 && byMj2 == byMj3) {
			block.first = byMj1;
			block.style = Constants.BLOCK_KE;
			return block;
		}

		// 顺形结构
		if (IsWST(byMj3) && IsWST(byMj1)) // 不为字, 花
		{
			if (byMj3 == byMj2 + 1 && byMj2 == byMj1 + 1) {
				block.first = byMj1;
				block.style = Constants.BLOCK_SUN;
				return block;
			}
		}
		return block;
	}

	// 是否可以做将牌
	public static boolean IsJiang(int byMj1, int byMj2) {
		if (byMj1 == byMj2 && MajHelper.IsWTSZ(byMj1)) {
			return true;
		}
		return false;
	}

	public static boolean IsTongHuaSe(int byMj1, int byMj21, int byMj31) {
		int byMj2 = byMj21;
		int byMj3 = byMj31;
		if (IsWan(byMj1) && IsWan(byMj2) && IsWan(byMj3)) {
			return true;
		}
		if (IsTong(byMj1) && IsTong(byMj2) && IsTong(byMj3)) {
			return true;
		}
		if (IsSuo(byMj1) && IsSuo(byMj2) && IsSuo(byMj3)) {
			return true;
		}
		if ((byMj1 == byMj2) && (byMj2 == byMj3) && MajHelper.IsWTSZ(byMj1)) {
			return true;
		}
		return false;
	}

	public static boolean IsTongHuaSe(int byMj1, int byMj2) {
		if (IsWan(byMj1) && IsWan(byMj2)) {
			return true;
		}
		if (IsTong(byMj1) && IsTong(byMj2)) {
			return true;
		}
		if (IsSuo(byMj1) && IsSuo(byMj2)) {
			return true;
		}

		if (byMj1 == byMj2 && MajHelper.IsWTSZ(byMj1)) {
			return true;
		}
		return false;
	}

	public static boolean IsWTSZ(int byMj) {
		if (byMj >= 1 && byMj <= 9)// 一万~九万
		{
			return true;
		}
		if (byMj >= 11 && byMj <= 19)// 一筒~九筒
		{
			return true;
		}
		if (byMj >= 21 && byMj <= 29)// 一条~九条
		{
			return true;
		}
		if (byMj >= 31 && byMj <= 37)// 东南西北中发白
		{
			return true;
		}
		if (byMj >= 41 && byMj <= 48)// 春夏秋冬梅兰竹菊
		{
			return true;
		}
		return false;
	}

	// 是否是万索筒 就是萬饼条
	public static boolean IsWST(int byMj1) {
		if (IsWan(byMj1)) {
			return true;
		}
		if (IsTong(byMj1)) {
			return true;
		}
		if (IsSuo(byMj1)) {
			return true;
		}
		return false;
	}

	public static boolean IsWan(int byMj1) {
		if (byMj1 >= 1 && byMj1 <= 9) {
			return true;
		}
		return false;
	}

	public static boolean IsTong(int byMj1) {
		if (byMj1 >= 11 && byMj1 <= 19) {
			return true;
		}
		return false;
	}

	public static boolean IsSuo(int byMj1) {
		if (byMj1 >= 21 && byMj1 <= 29) {
			return true;
		}
		return false;
	}

	// 是否是风牌
	public static boolean IsZi(int byMj1) {
		if (byMj1 >= 31 && byMj1 <= 37) {
			return true;
		}
		return false;
	}

	// 是否是东、南、西、北、中、发、白
	public static boolean IsDNXBZFB(int byMj1) {
		if (byMj1 >= 31 && byMj1 <= 37) {
			return true;
		}
		return false;
	}

	// 是否是风牌
	public static boolean IsFeng(int byMj1) {
		if (byMj1 >= 31 && byMj1 <= 37) {
			return true;
		}
		return false;
	}

	// 是否是三元
	public static boolean IsSanYuan(int byMj1) {
		if (byMj1 >= 35 && byMj1 <= 37) {
			return true;
		}
		return false;
	}

	public static boolean IsHua(int byMj1) {
		if (byMj1 >= 41 && byMj1 <= 48) {
			return true;
		}
		return false;
	}

	public static int GetNextUser(int bySeatID) {
		return (bySeatID + 1) % 4;
	}

	public static int GetPrevUser(int bySeatID) {
		return (bySeatID + 3) % 4;
	}

	// 是否是花牌
	public static boolean IsHuaPai(int byPai) {
		if (byPai >= 41 && byPai <= 48) {
			return true;
		}
		return false;
	}

	// 是否可以吃牌
	public static int IsChi(int byHandMj[], int byMj) {
		// 风,字不能上
		if (byMj >= 31) {
			return 0;
		}
		int chiInfo = 0; // 吃牌信息, 0-无吃牌,1-**@型, 2-*@*, 4-@**型
		boolean pos2, pos1, pos;
		pos2 = pos1 = pos = true;
		for (int i = 0; i < Constants.HAND_MJ_MAX - 1; i++) {
			// **@
			if (byHandMj[i] == byMj - 2 && pos2) {
				for (int j = i; j < Constants.HAND_MJ_MAX - 1; j++) {
					if (byHandMj[j] == byMj - 1
							&& IsTongHuaSe(byMj, byMj - 1, byMj - 2)) {
						chiInfo += 1; // 吃牌类型1
						break;
					}
				}
				pos2 = false;
			}
			// *@*
			else if (byHandMj[i] == byMj - 1 && pos1) {
				for (int j = i; j < Constants.HAND_MJ_MAX - 1; j++) {
					if (byHandMj[j] == byMj + 1
							&& IsTongHuaSe(byMj, byMj - 1, byMj + 1)) {
						chiInfo += 2; // 吃牌类型2
						break;
					}
				}
				pos1 = false;
			}
			// @**
			else if (byHandMj[i] == byMj + 1 && pos) {
				for (int j = i; j < Constants.HAND_MJ_MAX - 1; j++) {
					if (byHandMj[j] == byMj + 2
							&& IsTongHuaSe(byMj, byMj + 1, byMj + 2)) {
						chiInfo += 4; // 吃牌类型2
						break;
					}
				}
				pos = false;
			}
		}
		return chiInfo;
	}

	public static int IsChi(int byHandMj[], int byMj, int caishen) {
		if (byMj == caishen) {
			return 0;
		}
		int tmpMj[] = byHandMj.clone();
		for (int i = 0; i < tmpMj.length; i++) {
			int mj = tmpMj[i];
			if (mj == caishen) {
				tmpMj[i] = Constants.INVALID_CARD;
			} else if (mj == Constants.bai) {
				tmpMj[i] = caishen;
			}
		}
		if (byMj == Constants.bai) {
			byMj = caishen;
		}
		SortCard(tmpMj, Constants.HAND_MJ_MAX);
		return IsChi(tmpMj, byMj);
	}

	// 是否可以碰牌
	public static boolean IsPeng(int byHandMj[], int byMj) {
		for (int i = 0; i < Constants.HAND_MJ_MAX - 1 - 1; i++) {
			if (byHandMj[i] == byMj && byHandMj[i + 1] == byMj
					&& IsTongHuaSe(byMj, byHandMj[i], byHandMj[i + 1])) {
				return true;
			}
		}
		return false;
	}

	// 是否可以碰牌
	public static boolean IsPeng(int byHandMj[], int byMj, int caishen) {
		if (byMj == caishen) {// 别人出的财神
			return false;
		}
		// int tmpMj[] = byHandMj.clone();
		// for (int i = 0; i < tmpMj.length; i++) {
		// int mj = tmpMj[i];
		// if (mj == Constants.bai) {
		// tmpMj[i] = caishen;
		// }
		// }
		// if (byMj ==Constants.bai ) {
		// byMj = caishen;
		// }
		// SortCard(tmpMj);
		return IsPeng(byHandMj, byMj);
		/*
		 * if (byMj == Constants.bai || byMj == caishen) { int Num = 0; for (int
		 * i = 0; i < Constants.HAND_MJ_MAX - 1; i++) { int mj = byHandMj[i]; if
		 * ( mj == caishen || mj == Constants.bai) { Num++; } } if (Num >= 2) {
		 * return true; } }else{ return IsPeng(byHandMj, byMj); } return false;
		 */
	}

	// 是否明杠
	public static MJ_GANGINFO IsGang(int byHandMj[], int byMj) {
		MJ_GANGINFO gangInfo = new MJ_GANGINFO();
		gangInfo.GangStyle = 0;
		gangInfo.GangMj = 0;
		// 明杠手上不会有第十四张牌
		for (int i = 0; i < Constants.HAND_MJ_MAX - 3; i++) {
			if (byHandMj[i] == byMj && byHandMj[i + 1] == byMj
					&& byHandMj[i + 2] == byMj) {
				gangInfo.GangMj = byHandMj[i];
				gangInfo.GangStyle = 1;
			}
		}
		return gangInfo;
	}

	public static MJ_GANGINFO IsZMGang(int byHandMj[], HU hu) {
		return IsZMGang(byHandMj, hu, 255, 255, 255);
	}

	// 自摸明杠 返回,
	public static MJ_GANGINFO IsZMGang(int byHandMj[], HU hu, int jPos1,
			int jPos2, int jPos3) {
		MJ_GANGINFO gangInfo = new MJ_GANGINFO();
		gangInfo.GangStyle = 0;
		gangInfo.GangMj = Constants.INVALID_CARD;
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			if (hu.block[i].style == Constants.BLOCK_NULL)
				break;
			else if (hu.block[i].style != Constants.BLOCK_PENG)
				continue;
			else {
				// 跳过多个补杠
				if (hu.block[i].first == jPos1 || hu.block[i].first == jPos2
						|| hu.block[i].first == jPos3)
					continue;
				for (int j = 0; j < Constants.HAND_MJ_MAX; j++) {
					// if( byHandMj[j]==jPos1 || byHandMj[j]==jPos2 )
					// continue;
					if (byHandMj[j] == hu.block[i].first) {
						gangInfo.GangStyle = 2; // 自摸明杠
						gangInfo.GangMj = byHandMj[j]; // 明杠胡牌块位
						return gangInfo;
					}
				}
			}
		}
		return gangInfo;
	}

	public static MJ_GANGINFO IsAnGang(int byHandMj[]) {
		return IsAnGang(byHandMj, 255, 255, 255);
	}

	public static MJ_GANGINFO IsAnGang(int byHandMj[], int jPos1) {
		return IsAnGang(byHandMj, jPos1, 255, 255);
	}

	public static MJ_GANGINFO IsAnGang(int byHandMj[], int jPos1, int jPos2) {
		return IsAnGang(byHandMj, jPos1, jPos2, 255);
	}

	// 是否暗杠
	public static MJ_GANGINFO IsAnGang(int byHandMj[], int jPos1, int jPos2,
			int jPos3) {
		MJ_GANGINFO gangInfo = new MJ_GANGINFO();
		gangInfo.GangStyle = 0;
		gangInfo.GangMj = Constants.INVALID_CARD;
		for (int i = 0; i < Constants.HAND_MJ_MAX - 3; i++) {
			// 跳过
			if (byHandMj[i] == jPos1 || byHandMj[i] == jPos2
					|| byHandMj[i] == jPos3)
				continue;
			if (byHandMj[i] == byHandMj[i + 1]
					&& byHandMj[i] == byHandMj[i + 2]) {
				// 手上有杠牌
				if (byHandMj[i] == byHandMj[i + 3]) {
					gangInfo.GangStyle = 4;
					gangInfo.GangMj = byHandMj[i];
				}
				// 刚摸到杠牌
				else if (byHandMj[i] == byHandMj[Constants.HAND_MJ_MAX - 1]) {
					gangInfo.GangStyle = 4;
					gangInfo.GangMj = byHandMj[i];
				}
			}
		}
		return gangInfo;
	}

	// 清除胡牌数据
	public static void CleanHu(HU hu) {
		hu.jiangMj = Constants.INVALID_CARD;
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			if (hu.block[i] == null) {
				hu.block[i] = new BLOCK();
			}
			hu.block[i].first = Constants.INVALID_CARD;
			hu.block[i].style = Constants.BLOCK_NULL;
		}
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			hu.sanMj[i] = Constants.INVALID_CARD;
		}
	}

	// 拷贝胡牌数据
	public static void CopyHu(HU destHu, HU srcHu) {
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			destHu.block[i].first = srcHu.block[i].first;
			destHu.block[i].style = srcHu.block[i].style;
		}
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			destHu.sanMj[i] = srcHu.sanMj[i];
		}
	}

	public static void HuToHandMj(int byMjs[], HU srcHu) {
		int j = 0;
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			switch (srcHu.block[i].style) {
			case Constants.BLOCK_NULL: {

			}
				break;
			case Constants.BLOCK_CHI: {
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = (srcHu.block[i].first + 1);
				byMjs[j++] = (srcHu.block[i].first + 2);
			}
				break;
			case Constants.BLOCK_SUN: // 顺序结构
			{
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = (srcHu.block[i].first + 1);
				byMjs[j++] = (srcHu.block[i].first + 2);
			}
				break;
			case Constants.BLOCK_PENG: // 碰子结构,3个相同
			{
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
			}
				break;
			case Constants.BLOCK_KE: // 刻子结构,3个相同,非碰
			{
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
			}
				break;
			case Constants.BLOCK_GANG: // 杠子结构,4个相同
			case Constants.BLOCK_BU_GANG: {
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
			}
				break;
			case Constants.BLOCK_AN_GANG: // 暗杠
			{
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
				byMjs[j++] = srcHu.block[i].first;
			}
				break;
			}
		}
		int srcHujiangMj = srcHu.jiangMj;
		byMjs[j++] = srcHujiangMj;
		byMjs[j++] = srcHujiangMj;
	}

	public static int DeletePai(int byHandMj[], int byMj1) {
		return DeletePai(byHandMj, byMj1, 255, 255);
	}

	public static int DeletePai(int byHandMj[], int byMj1, int byMj2) {
		return DeletePai(byHandMj, byMj1, byMj2, 255);
	}

	public static int DeletePai(int byHandMj[], int byMj1, int byMj2, int byMj3) {
		int cnt = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (byHandMj[i] == byMj1 && byMj1 != Constants.INVALID_CARD) {
				byHandMj[i] = Constants.INVALID_CARD;
				byMj1 = Constants.INVALID_CARD;
				cnt++;
			}
			if (byHandMj[i] == byMj2 && byMj2 != Constants.INVALID_CARD) {
				byHandMj[i] = Constants.INVALID_CARD;
				byMj2 = Constants.INVALID_CARD;
				cnt++;
			}
			if (byHandMj[i] == byMj3 && byMj3 != Constants.INVALID_CARD) {
				byHandMj[i] = Constants.INVALID_CARD;
				byMj3 = Constants.INVALID_CARD;
				cnt++;
			}
		}
		SortCard(byHandMj, Constants.HAND_MJ_MAX);
		return cnt;
	}

	public static void AdjustChiHu(HU hu, int byHuMj) {
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_KE: {
				if (hu.block[i].first == byHuMj) {
					hu.block[i].style = Constants.BLOCK_PENG;
				}
			}
			default:
				break;
			}
		}
	}

	// 分析胡牌类型,返回番数
	public static long CheckGDHu(HU hu, int byFengWei, int byQuanWei,
			char strFang) {
		return 0;
	}

	public static BLOCK Peng(int byMjs[], int byMj, int caishen[]) {
		return Peng(byMjs, byMj, caishen[0]);
	}

	public static BLOCK Peng(int byMjs[], int byMj, int caishen) {
		if (byMj == Constants.bai) {
			int baiNum = 0;
			for (int i = 0; i < Constants.HAND_MJ_MAX - 1 && baiNum < 2; i++) {
				int mj = byMjs[i];
				if (mj == Constants.bai) {// 优先白板去碰
					byMjs[i] = Constants.INVALID_CARD;
					baiNum++;
				}
			}
			for (int i = 0; i < Constants.HAND_MJ_MAX - 1 && baiNum < 2; i++) {
				int mj = byMjs[i];
				if (mj == caishen) {// 不够用财神补上
					byMjs[i] = Constants.INVALID_CARD;
					baiNum++;
				}
			}
			MJ_BLOCK block = new MJ_BLOCK();
			block.first = byMj;
			block.style = Constants.BLOCK_PENG;
			return block;
		} else {
			return Peng(byMjs, byMj);
		}
	}

	public static BLOCK Peng(int byMjs[], int byMj) {
		MJ_BLOCK block = new MJ_BLOCK();
		for (int i = 0; i < Constants.HAND_MJ_MAX - 1; i++) {
			if (byMjs[i] == byMj && byMjs[i + 1] == byMj) {// 普通碰
				byMjs[i] = Constants.INVALID_CARD;
				byMjs[i + 1] = Constants.INVALID_CARD;
				// 右移3格
				break;
			}
		}
		block.first = byMj;
		block.style = Constants.BLOCK_PENG;
		return block;
	}

	// 杠操作
	public static BLOCK MGang(int byMjs[], int byMj) {
		MJ_BLOCK block = new MJ_BLOCK();
		block.style = Constants.BLOCK_NULL;
		block.first = -1;
		for (int i = 0; i < Constants.HAND_MJ_MAX - 3; i++) {
			if (byMjs[i] == byMj) {
				byMjs[i] = Constants.INVALID_CARD;
				byMjs[i + 1] = Constants.INVALID_CARD;
				byMjs[i + 2] = Constants.INVALID_CARD;
				block.style = Constants.BLOCK_GANG;
				block.first = byMj;
				// 右移4格
				return block;
			}
		}
		return block;
	}

	// 自摸明杠-补杠
	public static void ZMGang(int byMjs[], HU hu, int GangMj) {
		for (int i = 0; i < (Constants.HAND_MJ_MAX - 2) / 3; i++) {
			if (hu.block[i].first == GangMj) {
				hu.block[i].style = Constants.BLOCK_BU_GANG;
				break;// 右移一格
			}
		}
		for (int j = 0; j < Constants.HAND_MJ_MAX; j++) {
			if (byMjs[j] == GangMj) {
				byMjs[j] = Constants.INVALID_CARD;
				break;
			}
		}
	}

	// 暗杠
	public static BLOCK AnGang(int byMjs[], int GangMj) {
		MJ_BLOCK block = new MJ_BLOCK();
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (byMjs[i] == GangMj) {
				byMjs[i] = Constants.INVALID_CARD;
			}
		}
		block.style = Constants.BLOCK_AN_GANG;
		block.first = GangMj;
		return block;
	}

	public static BLOCK Chi(int byMjs[], int byMj, int ChiMode, int caishen[]) {
		return Chi(byMjs, byMj, ChiMode, caishen[0]);
	}

	public static BLOCK Chi(int byMjs[], int byMj, int ChiMode, int caishen) {
		int OriginalMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(OriginalMj, byMjs, Constants.HAND_MJ_MAX);

		int cntCS = 0;

		if (caishen != Constants.INVALID_CARD) {
			cntCS = Constants.countof(OriginalMj, caishen,
					Constants.HAND_MJ_MAX);
			Constants.replace(OriginalMj, caishen, Constants.INVALID_CARD);
			Constants.replace(OriginalMj, bai, caishen);
		}
		if (byMj == bai) {
			byMj = caishen;
		}
		MajHelper.SortCard(OriginalMj, (int) Constants.HAND_MJ_MAX);
		MJ_BLOCK block = new MJ_BLOCK();
		block.first = 0;
		block.style = Constants.BLOCK_NULL;
		switch (ChiMode) {
		case 1: // @@*
		{
			block.first = (byMj - 2);
			block.style = Constants.BLOCK_CHI;
			// 清零麻将
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (OriginalMj[i] == byMj - 2) {
					OriginalMj[i] = Constants.INVALID_CARD;
					for (int j = i; j < Constants.HAND_MJ_MAX; j++) {
						if (OriginalMj[j] == byMj - 1) {
							OriginalMj[j] = Constants.INVALID_CARD;
							Constants.memcpy(byMjs, OriginalMj,
									Constants.HAND_MJ_MAX);
							if (caishen != Constants.INVALID_CARD) {
								Constants.replace(byMjs, caishen, bai);
								Constants.replace(byMjs,
										Constants.INVALID_CARD, caishen, cntCS);
							}
							if (Constants.countof(byMjs, caishen,
									Constants.HAND_MJ_MAX) > 2) {
								System.out.println("CHI 1:"
										+ IJsonExport.sprintf_INT32(byMjs, 14));
							}
							MajHelper.SortCard(byMjs,
									(int) Constants.HAND_MJ_MAX);
							if (Constants.countof(byMjs, caishen,
									Constants.HAND_MJ_MAX) > 2) {
								System.out.println("CHI 1:"
										+ IJsonExport.sprintf_INT32(byMjs, 14));
							}
							return block;
						}
					}
					break;
				}
			}

		}
			break;
		case 2: // @*@
		{
			block.first = (byMj - 1);
			block.style = Constants.BLOCK_CHI;
			// 清零麻将
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (OriginalMj[i] == byMj - 1) {
					OriginalMj[i] = Constants.INVALID_CARD;
					for (int j = i; j < Constants.HAND_MJ_MAX; j++) {
						if (OriginalMj[j] == byMj + 1) {
							OriginalMj[j] = Constants.INVALID_CARD;
							Constants.memcpy(byMjs, OriginalMj,
									Constants.HAND_MJ_MAX);
							if (caishen != Constants.INVALID_CARD) {
								Constants.replace(byMjs, caishen, bai);
								Constants.replace(byMjs,
										Constants.INVALID_CARD, caishen, cntCS);
							}
							if (Constants.countof(byMjs, caishen,
									Constants.HAND_MJ_MAX) > 2) {
								System.out.println("CHI 2:"
										+ IJsonExport.sprintf_INT32(byMjs, 14));
							}
							MajHelper.SortCard(byMjs,
									(int) Constants.HAND_MJ_MAX);
							if (Constants.countof(byMjs, caishen,
									Constants.HAND_MJ_MAX) > 2) {
								System.out.println("CHI 2:"
										+ IJsonExport.sprintf_INT32(byMjs, 14));
							}

							return block;
						}
					}
					break;
				}
			}
		}
			break;
		case 4: // *@@
		{
			block.first = byMj;
			block.style = Constants.BLOCK_CHI;
			// 清零麻将
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (OriginalMj[i] == byMj + 1) {
					OriginalMj[i] = Constants.INVALID_CARD;
					for (int j = i; j < Constants.HAND_MJ_MAX; j++) {
						if (OriginalMj[j] == byMj + 2) {
							OriginalMj[j] = Constants.INVALID_CARD;
							Constants.memcpy(byMjs, OriginalMj,
									Constants.HAND_MJ_MAX);
							if (caishen != Constants.INVALID_CARD) {
								Constants.replace(byMjs, caishen, bai);
								Constants.replace(byMjs,
										Constants.INVALID_CARD, caishen, cntCS);
							}
							if (Constants.countof(byMjs, caishen,
									Constants.HAND_MJ_MAX) > 2) {
								System.out.println("CHI 4:"
										+ IJsonExport.sprintf_INT32(byMjs, 14));
							}
							MajHelper.SortCard(byMjs,
									(int) Constants.HAND_MJ_MAX);
							if (Constants.countof(byMjs, caishen,
									Constants.HAND_MJ_MAX) > 2) {
								System.out.println("CHI 4:"
										+ IJsonExport.sprintf_INT32(byMjs, 14));
							}
							return block;
						}
					}
					break;
				}
			}
		}
			break;
		}

		return block;
	}

	// 吃牌操作
	public static BLOCK Chi(int byMjs[], int byMj, int ChiMode) {
		MJ_BLOCK block = new MJ_BLOCK();
		block.first = 0;
		block.style = Constants.BLOCK_NULL;
		switch (ChiMode) {
		case 1: // @@*
		{
			block.first = (byMj - 2);
			block.style = Constants.BLOCK_CHI;
			// 清零麻将
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (byMjs[i] == byMj - 2) {
					byMjs[i] = Constants.INVALID_CARD;
					for (int j = i; j < Constants.HAND_MJ_MAX; j++) {
						if (byMjs[j] == byMj - 1) {
							byMjs[j] = Constants.INVALID_CARD;
							return block;
						}
					}
					break;
				}
			}
		}
			break;
		case 2: // @*@
		{
			block.first = (byMj - 1);
			block.style = Constants.BLOCK_CHI;
			// 清零麻将
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (byMjs[i] == byMj - 1) {
					byMjs[i] = Constants.INVALID_CARD;
					for (int j = i; j < Constants.HAND_MJ_MAX; j++) {
						if (byMjs[j] == byMj + 1) {
							byMjs[j] = Constants.INVALID_CARD;
							return block;
						}
					}
					break;
				}
			}
		}
			break;
		case 4: // *@@
		{
			block.first = byMj;
			block.style = Constants.BLOCK_CHI;
			// 清零麻将
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (byMjs[i] == byMj + 1) {
					byMjs[i] = Constants.INVALID_CARD;
					for (int j = i; j < Constants.HAND_MJ_MAX; j++) {
						if (byMjs[j] == byMj + 2) {
							byMjs[j] = Constants.INVALID_CARD;
							return block;
						}
					}
					break;
				}
			}
		}
			break;
		}
		return block;
	}

	public static int GetFengZiKe(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsFeng(hu.block[i].first)) {
				total++;
			}
		}
		return total;
	}

	public static int GetSanYuanKe(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsSanYuan(hu.block[i].first)) {
				total++;
			}
		}
		return total;
	}

	/**
	 * 牌型暗刻
	 * 
	 * @param tempMj
	 * @param hu
	 * @return
	 */
	public static int GetPaiXinAnKe(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_KE:
			case Constants.BLOCK_AN_GANG: {
				total++;
			}
			}
		}
		return total;
	}

	public static int GetPaiXinAnKe(int tempMj[], HU hu, int caishen) {

		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {

			switch (hu.block[i].style) {
			case Constants.BLOCK_KE:
			case Constants.BLOCK_AN_GANG: {
				total++;
			}
			}
		}
		return total;
	}

	public static boolean IsBaXianGuoHai(int byHuaPai[], int byMj) {
		int iHuaCount = 0;
		for (int j = 0; j < 8; j++) {
			if (IsHuaPai(byHuaPai[j])) {
				iHuaCount++;
			}
		}
		if (IsHuaPai(byMj)) {
			iHuaCount++;
		}
		if (iHuaCount == 8) {
			return true;
		} else {
			return false;
		}
	}

	// 平胡
	public static boolean IsPaiXinPinHu(int tempMj[], HU hu, int byMj) {
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (tempMj[i] >= 31) {
				return false;
			}
		}
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG:
			case Constants.BLOCK_BU_GANG: {
				return false;
			}
			}
		}
		if (hu.jiangMj >= 31) {
			return false;
		}
		boolean bDuTing = false;
		boolean bDuoTing = false;
		int sunMjtotal = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_SUN: {
				sunMjtotal++;
				if (hu.block[i].first == byMj) // @**
				{
					if (hu.block[i].first % 10 == 7) // 7,89
					{
						bDuTing = true;
					} else {
						bDuoTing = true;
					}
				}
				if (hu.block[i].first == byMj - 1
						&& IsTongHuaSe(byMj, byMj - 1)) // *@*
				{
					bDuTing = true;
				}
				if (hu.block[i].first == byMj - 2
						&& IsTongHuaSe(byMj, byMj - 2)) // **@
				{
					if (hu.block[i].first % 10 == 1) // 12,3
					{
						bDuTing = true;
					} else {
						bDuoTing = true;
					}
				}
			}
				break;
			default: {
				return false;
			}
			}
		}
		if (sunMjtotal == 4) {
			if (bDuoTing) {
				return true;
			}
		}
		return false;
	}

	/**
	 * 牌型门清
	 * 
	 * @param tempMj
	 * @param hu
	 * @return
	 */
	public static boolean IsPaiXinMenQing(int tempMj[], HU hu) {
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_BU_GANG: {
				return false;
			}
			}
		}
		return true;
	}

	public static boolean IsPaiXinQuanQiu(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_GANG: {
				total++;
			}
				break;
			}
		}
		if (total == Constants.MAX_BLOCK_NUM) {
			return true;
		} else {
			return false;
		}
	}

	public static boolean IsPaiXinZiYiSe(int tempMj[], HU hu) {
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (IsFeng(tempMj[i]) || IsSanYuan(tempMj[i])) {
			} else {
				return false;
			}
		}
		return true;
	}

	public static boolean IsPaiXinCouYiSe(int tempMj[], HU hu) {
		int iWanCount = 0, iSuoCount = 0, iTongCount = 0, iZiCount = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (IsWan(tempMj[i])) {
				iWanCount++;
			} else if (IsTong(tempMj[i])) {
				iSuoCount++;
			} else if (IsSuo(tempMj[i])) {
				iTongCount++;
			} else if (IsZi(tempMj[i])) {
				iZiCount++;
			}
		}
		if (iZiCount == Constants.HAND_MJ_MAX) {
			return false;
		}
		if (iWanCount + iZiCount == Constants.HAND_MJ_MAX
				|| iSuoCount + iZiCount == Constants.HAND_MJ_MAX
				|| iTongCount + iZiCount == Constants.HAND_MJ_MAX) {
			return true;
		}
		return false;
	}

	public static boolean IsPaiXinSiAnKe(int tempMj[], HU hu) {
		if (GetPaiXinAnKe(tempMj, hu) == 4) {
			return true;
		}
		return false;
	}

	// 断幺九
	public static boolean IsPaiXinDuanYaoJiu(int tempMj[], HU hu) {
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (IsZi(tempMj[i]) || tempMj[i] % 10 == 1 || tempMj[i] % 10 == 9) {
				return false;
			}
		}
		return true;
	}

	// 一杯口
	// 板班gao
	public static boolean IsPaiXinYiBeiKou(int tempMj[], HU hu) {
		if (!IsPaiXinMenQing(tempMj, hu)) {
			return false;
		}
		int total = 0;
		int bySunMj[] = new int[5];

		Constants.memset(bySunMj, Constants.INVALID_CARD,
				Constants.sizeof(bySunMj));

		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_SUN: {
				bySunMj[total++] = hu.block[i].first;
			}
				break;
			default:
				break;
			}
		}
		int bei_kou = 0;
		if (total >= 2) {
			for (int j = 0; j < total - 1; j++) {
				if (bySunMj[j] == bySunMj[j + 1]) {
					bei_kou++;
					j += 1;
				}
			}
		}
		if (bei_kou == 1) {
			return true;
		}
		return false;
	}

	// 二杯口
	public static boolean IsPaiXinErBeiKou(int tempMj[], HU hu) {
		if (!IsPaiXinMenQing(tempMj, hu)) {
			return false;
		}
		int total = 0;
		int bySunMj[] = new int[5];

		Constants.memset(bySunMj, Constants.INVALID_CARD,
				Constants.sizeof(bySunMj));

		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_SUN: {
				bySunMj[total++] = hu.block[i].first;
			}
				break;
			default:
				break;
			}
		}
		int bei_kou = 0;
		if (total >= 2) {
			for (int j = 0; j < total - 1; j++) {
				if (bySunMj[j] == bySunMj[j + 1]) {
					bei_kou++;
					j += 1;
				}
			}
		}
		if (bei_kou == 2) {
			return true;
		}
		return false;
	}

	// 七对子
	public static boolean IsPaiXinQiDuiZi(int tempMj[], HU hu) {
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_SUN:
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG: {
				return false;
			}
			default:
				break;
			}
		}
		int MjDuiZiCount = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX - 1; i += 2) {
			if (tempMj[i] != Constants.INVALID_CARD
					&& tempMj[i] == tempMj[i + 1]) {
				MjDuiZiCount++;
			}
		}
		if (MjDuiZiCount == 7) {
			return true;
		}
		return false;
	}

	public static boolean IsPaiXinDuiDuiHu(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG:
			case Constants.BLOCK_BU_GANG: {
				total++;
			}
			default:
				break;
			}
		}
		if (total == Constants.MAX_BLOCK_NUM) {
			return true;
		} else {
			return false;
		}
	}

	// 全带幺
	public static boolean IsPaiXinQuanDaiYao(int tempMj[], HU hu) {
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_SUN: {
				if (hu.block[i].first % 10 != 1 && hu.block[i].first % 10 != 7) {
					return false;
				}
			}
				break;
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG:
			case Constants.BLOCK_BU_GANG: {
				if (hu.block[i].first % 10 != 1 && hu.block[i].first % 10 != 9) {
					return false;
				}
			}
				break;
			default: {
				return false;
			}
			}
		}
		if (hu.jiangMj >= 31 || (hu.jiangMj % 10 != 1 && hu.jiangMj % 10 != 9)) {
			return false;
		}
		return true;
	}

	// 混全带幺
	public static boolean IsPaiXinHunDaiYao(int tempMj[], HU hu) {
		boolean bZiPai = false;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (MajHelper.IsWTSZ(hu.block[i].first)) {
				switch (hu.block[i].style) {
				case Constants.BLOCK_CHI:
				case Constants.BLOCK_SUN: {
					if (hu.block[i].first % 10 != 1
							&& hu.block[i].first % 10 != 7) {
						return false;
					}
				}
					break;
				case Constants.BLOCK_PENG:
				case Constants.BLOCK_KE:
				case Constants.BLOCK_GANG:
				case Constants.BLOCK_AN_GANG:
				case Constants.BLOCK_BU_GANG: {
					if (IsZi(hu.block[i].first)) {
						bZiPai = true;
					} else if (hu.block[i].first % 10 != 1
							&& hu.block[i].first % 10 != 7) {
						return false;
					}
				}
					break;
				default: {
					return false;
				}
				}
			}
		}
		if (bZiPai || IsZi(hu.jiangMj)) {
			return true;
		}
		return false;
	}

	// 混老头
	public static boolean IsPaiXinHunLaoTou(int tempMj[], HU hu) {
		boolean bZiPai = false;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (MajHelper.IsWTSZ(hu.block[i].first)) {
				switch (hu.block[i].style) {
				case Constants.BLOCK_CHI:
				case Constants.BLOCK_SUN: {
					return false;
				}
				case Constants.BLOCK_PENG:
				case Constants.BLOCK_KE:
				case Constants.BLOCK_GANG:
				case Constants.BLOCK_AN_GANG:
				case Constants.BLOCK_BU_GANG: {
					if (IsZi(hu.block[i].first)) {
						bZiPai = true;
					} else if (hu.block[i].first % 10 != 1
							&& hu.block[i].first % 10 != 9) {
						return false;
					}
				}
					break;
				default: {
					return false;
				}
				}
			}
		}
		if (bZiPai || IsZi(hu.jiangMj)) {
			return true;
		}
		return false;
	}

	// 清一色
	public static boolean IsPaiXinQingYiSe(int tempMj[], HU hu) {

		int iWanCount = 0, iSuoCount = 0, iTongCount = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (IsWan(tempMj[i])) {
				iWanCount++;
			} else if (IsTong(tempMj[i])) {
				iTongCount++;
			} else if (IsSuo(tempMj[i])) {
				iSuoCount++;
			} else if (IsZi(tempMj[i])) {
				return false;
			}
		}
		if (iWanCount == Constants.HAND_MJ_MAX
				|| iSuoCount == Constants.HAND_MJ_MAX
				|| iTongCount == Constants.HAND_MJ_MAX) {
			return true;
		}
		return false;
	}

	// 混一色
	public static boolean IsPaiXinHunYiSe(int tempMj[], HU hu) {
		int iWanCount = 0, iSuoCount = 0, iTongCount = 0, iZiCount = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (IsWan(tempMj[i])) {
				iWanCount++;
			} else if (IsTong(tempMj[i])) {
				iTongCount++;
			} else if (IsSuo(tempMj[i])) {
				iSuoCount++;
			} else if (IsZi(tempMj[i])) {
				iZiCount++;
			}
		}
		if (iZiCount == Constants.HAND_MJ_MAX) {
			return false;
		}
		if (iZiCount > 0) {
			if (iWanCount + iZiCount == Constants.HAND_MJ_MAX
					|| iSuoCount + iZiCount == Constants.HAND_MJ_MAX
					|| iTongCount + iZiCount == Constants.HAND_MJ_MAX) {
				return true;
			}
		}
		return false;
	}

	// 一气通贯
	public static boolean IsPaiXinYiQiTongGuan(int tempMj[], HU hu) {
		int bySunMj[] = new int[4];

		Constants.memset(bySunMj, Constants.INVALID_CARD,
				Constants.sizeof(bySunMj));

		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_SUN: {
				bySunMj[total++] = hu.block[i].first;
			}
				break;
			default:
				break;
			}
		}
		if (total >= 3) {
			for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
				boolean bj3 = false;
				boolean bj6 = false;
				for (int j = i; j < Constants.MAX_BLOCK_NUM; j++) {
					if (i != j) {
						if (bySunMj[j] == bySunMj[i] + 3
								&& IsTongHuaSe(bySunMj[j], bySunMj[i])) {
							bj3 = true;
						}
						if (bySunMj[j] == bySunMj[i] + 6
								&& IsTongHuaSe(bySunMj[j], bySunMj[i])) {
							bj6 = true;
						}
					}
				}
				if (bj3 && bj6) {
					return true;
				}
			}
		}

		return false;
	}

	// 小三元
	public static boolean IsPaiXinXiaoSanYuan(int tempMj[], HU hu) {
		if (IsSanYuan(hu.jiangMj) == false) {
			return false;
		}
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsSanYuan(hu.block[i].first)) {
				total++;
			}
		}
		if (total == 2) {
			return true;
		}
		return false;
	}

	// 三色同顺
	public static boolean IsPaiXinSanSeTongShun(int tempMj[], HU hu) {
		int bySunMj[] = new int[5];

		Constants.memset(bySunMj, Constants.INVALID_CARD,
				Constants.sizeof(bySunMj));

		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_SUN: {
				bySunMj[total++] = hu.block[i].first;
			}
				break;
			default:
				break;
			}
		}
		if (total >= 3) {
			for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
				boolean bjw = false;
				boolean bjt = false;
				for (int j = i; j < Constants.MAX_BLOCK_NUM; j++) {
					if (i != j) {
						if (MajHelper.IsWTSZ(bySunMj[j])
								&& bySunMj[j] == bySunMj[i] + 10) {
							bjw = true;
						}
						if (MajHelper.IsWTSZ(bySunMj[j])
								&& bySunMj[j] == bySunMj[i] + 20) {
							bjt = true;
						}
					}
				}
				if (bjw && bjt) {
					return true;
				}
			}
		}

		return false;
	}

	// 一色三顺
	public static boolean IsPaiXinYiSeSanShun(int tempMj[], HU hu) {
		int bySunMj[] = new int[4];

		Constants.memset(bySunMj, Constants.INVALID_CARD,
				Constants.sizeof(bySunMj));

		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_CHI:
			case Constants.BLOCK_SUN: {
				bySunMj[total++] = hu.block[i].first;
			}
				break;
			default:
				break;
			}
		}
		if (total >= 3) {
			for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
				int count = 0;
				for (int j = i; j < Constants.MAX_BLOCK_NUM; j++) {
					if (i != j) {
						if (MajHelper.IsWTSZ(bySunMj[j])
								&& bySunMj[j] == bySunMj[i]) {
							count++;
						}
					}
				}
				if (count == 3) {
					return true;
				}
			}
		}

		return false;
	}

	// 三色同刻
	public static boolean IsPaiXinSanSeTongKe(int tempMj[], HU hu) {
		int byKeMj[] = new int[4];

		Constants.memset(byKeMj, Constants.INVALID_CARD,
				Constants.sizeof(byKeMj));

		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG:
			case Constants.BLOCK_BU_GANG: {
				if (IsWST(hu.block[i].first)) {
					byKeMj[total++] = hu.block[i].first;
				}
			}
				break;
			default:
				break;
			}
		}
		if (total >= 3) {
			for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
				boolean bjw = false;
				boolean bjt = false;
				for (int j = i; j < Constants.MAX_BLOCK_NUM; j++) {
					if (i != j) {
						if (MajHelper.IsWTSZ(byKeMj[j])
								&& byKeMj[j] == byKeMj[i] + 10) {
							bjw = true;
						}
						if (MajHelper.IsWTSZ(byKeMj[j])
								&& byKeMj[j] == byKeMj[i] + 20) {
							bjt = true;
						}
					}
				}
				if (bjw && bjt) {
					return true;
				}
			}
		}

		return false;
	}

	// 三暗刻
	public static boolean IsPaiXinSanAnKe(int tempMj[], HU hu) {
		if (GetPaiXinAnKe(tempMj, hu) == 3) {
			return true;
		}
		return false;
	}

	// 三连刻
	public static boolean IsPaiXinSanLianKe(int tempMj[], HU hu) {
		int byKeMj[] = new int[4];

		Constants.memset(byKeMj, Constants.INVALID_CARD,
				Constants.sizeof(byKeMj));

		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG:
			case Constants.BLOCK_BU_GANG: {
				if (IsZi(hu.block[0].first)) {
					return false;
				}
				byKeMj[total++] = hu.block[i].first;
			}
				break;
			default:
				break;
			}
		}
		if (total >= 3) {
			for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
				int count = 0;
				for (int j = i; j < Constants.MAX_BLOCK_NUM; j++) {
					if (i != j) {
						if ((byKeMj[j] == byKeMj[i] + 1 && IsTongHuaSe(
								byKeMj[j], byKeMj[i] + 1))
								|| (byKeMj[j] == byKeMj[i] + 2 && IsTongHuaSe(
										byKeMj[j], byKeMj[i] + 2))) {
							count++;
						}
					}
				}
				if (count == 3) {
					return true;
				}
			}
		}

		return false;
	}

	// 三杠子
	public static boolean IsPaiXinSanGangZi(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_AN_GANG:
			case Constants.BLOCK_BU_GANG: {
				total++;
			}
				break;
			default:
				break;
			}
		}
		if (total == 3) {
			return true;
		}
		return false;
	}

	// 字一色
	public static boolean IsZiYiSe(int tempMj[], HU hu) {
		int total = 0;
		if (IsWST(hu.jiangMj)) {
			return false;
		}
		if (IsPaiXinQiDuiZi(tempMj, hu)) {
			for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
				if (!IsZi(tempMj[i])) {
					return false;
				}
			}
			return true;
		}
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_KE:
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_BU_GANG:
			case Constants.BLOCK_AN_GANG: {
				if (IsZi(hu.block[i].first)) {
					total++;
				} else {
					return false;
				}
			}
				break;
			default: {
				return false;
			}
			}
		}
		if (total == 4) {
			return true;
		}
		return false;
	}

	public static boolean IsSiAnKe(int handMj[], HU hu) {
		if (GetPaiXinAnKe(handMj, hu) == 4) {
			return true;
		}
		int total = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX - 2; i++) {
			if (MajHelper.IsWTSZ(handMj[i]) && handMj[i] == handMj[i + 1]
					&& handMj[i + 1] == handMj[i + 2]) {
				total++;
				i += 2;
			}
		}
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_AN_GANG: {
				total++;
			}
			default:
				break;
			}
		}
		return false;
	}

	public static boolean IsDaSiXi(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsFeng(hu.block[i].first)) {
				total++;
			}
		}
		if (total == 4) {
			return true;
		}
		return false;
	}

	public static boolean IsXiaoSiXi(int tempMj[], HU hu) {
		if (IsFeng(hu.jiangMj) == false) {
			return false;
		}
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsFeng(hu.block[i].first)) {
				total++;
			}
		}
		if (total == 3) {
			return true;
		}
		return false;
	}

	public static boolean IsDaSanYuan(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsSanYuan(hu.block[i].first)) {
				total++;
			}
		}
		if (total == 3) {
			return true;
		}
		return false;
	}

	// 四连刻
	public static boolean IsSiLianKe(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (MajHelper.IsWTSZ(hu.block[0].first)) {
				switch (hu.block[i].style) {
				case Constants.BLOCK_PENG:
				case Constants.BLOCK_KE:
				case Constants.BLOCK_GANG:
				case Constants.BLOCK_BU_GANG:
				case Constants.BLOCK_AN_GANG: {
					if (IsZi(hu.block[0].first)) {
						return false;
					}
					total++;
				}
					break;
				default: {
					return false;
				}

				}
			}
		}
		if (total == 4) {
			if (IsTongHuaSe(hu.block[0].first, hu.block[1].first,
					hu.block[2].first)
					&& IsTongHuaSe(hu.block[1].first, hu.block[2].first,
							hu.block[3].first)) {
				if (hu.block[3].first == hu.block[2].first + 1
						&& hu.block[2].first + 1 == hu.block[1].first + 2
						&& hu.block[1].first + 2 == hu.block[0].first + 3) {
					return true;
				}
			} else {
				return false;
			}
		}
		return false;
	}

	// 四扛子
	public static boolean IsSiGangZi(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_BU_GANG:
			case Constants.BLOCK_AN_GANG: {
				total++;
			}
				break;
			default: {
				return false;
			}

			}
		}
		if (total == 4) {
			return true;
		}
		return false;
	}

	// 国士无双
	public static boolean IsGuoShiWuShuang(int tempMj[]) {
		if (GetPaiCount(tempMj) != Constants.HAND_MJ_MAX) {
			return false;
		}
		int intmpMj[] = new int[Constants.HAND_MJ_MAX];

		Constants.memset(intmpMj, Constants.INVALID_CARD,
				Constants.sizeof(intmpMj));

		Constants.memcpy(intmpMj, tempMj, Constants.HAND_MJ_MAX);
		int gswsMj[] = { 1, 9, 11, 19, 21, 29, 31, 32, 33, 34, 35, 36, 37,
				Constants.INVALID_CARD };
		// int mjCount = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX - 1; i++) {
			if (intmpMj[i] == intmpMj[i + 1]) {
				DeletePai(intmpMj, intmpMj[i]);
				break;
			}
		}
		SortCard(intmpMj, Constants.HAND_MJ_MAX);
		if (Constants.memcmp(intmpMj, gswsMj, Constants.HAND_MJ_MAX) == 0) {
			return true;
		}
		return false;
	}

	// 九莲宝灯
	public static boolean IsJiuLianBaoDeng(int tempMj[], HU hu) {
		if (GetPaiCount(tempMj) != Constants.HAND_MJ_MAX) {
			return false;
		}
		if (tempMj[0] + 8 == tempMj[Constants.HAND_MJ_MAX - 1]
				&& IsTongHuaSe(tempMj[0], tempMj[Constants.HAND_MJ_MAX - 1])) {
			boolean bYao = false;
			boolean bJiu = false;
			if (tempMj[0] == tempMj[1] && tempMj[1] == tempMj[2]
					&& tempMj[0] % 10 == 1) {
				bYao = true;
			}
			if (tempMj[Constants.HAND_MJ_MAX - 1] == tempMj[Constants.HAND_MJ_MAX - 2]
					&& tempMj[Constants.HAND_MJ_MAX - 2] == tempMj[Constants.HAND_MJ_MAX - 3]
					&& tempMj[Constants.HAND_MJ_MAX - 1] % 10 == 9) {
				bJiu = true;
			}
			if (bYao && bJiu) {
				int intmpMj[] = new int[Constants.HAND_MJ_MAX];

				Constants.memset(intmpMj, Constants.INVALID_CARD,
						Constants.sizeof(intmpMj));

				Constants.memcpy(intmpMj, tempMj, Constants.HAND_MJ_MAX);
				DeletePai(intmpMj, tempMj[0], tempMj[1], tempMj[2]);
				DeletePai(intmpMj, tempMj[Constants.HAND_MJ_MAX - 1],
						tempMj[Constants.HAND_MJ_MAX - 2],
						tempMj[Constants.HAND_MJ_MAX - 3]);

				for (int j = 2; j < 9; j++) {
					int mjCount = 0;
					for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
						if (MajHelper.IsWTSZ(intmpMj[i])
								&& intmpMj[i] % 10 == j) {
							mjCount++;
							break;
						}
					}
					if (mjCount == 0) {
						return false;
					}
				}

				return true;
			}
		}

		return false;
	}

	// 清老头
	public static boolean IsQingLaoTou(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (MajHelper.IsWTSZ(hu.block[i].first)) {
				switch (hu.block[i].style) {
				case Constants.BLOCK_PENG:
				case Constants.BLOCK_KE:
				case Constants.BLOCK_GANG:
				case Constants.BLOCK_BU_GANG:
				case Constants.BLOCK_AN_GANG: {
					if (hu.block[i].first % 10 == 1
							|| hu.block[i].first % 10 == 9) {
						total++;
					}
				}
					break;
				default: {
					return false;
				}

				}
			}

		}
		if (total == 4) {
			if (hu.jiangMj % 10 == 1 || hu.jiangMj % 10 == 9) {
				return true;
			}
		}
		return false;
	}

	// 绿一色
	public static boolean IsLvYiSe(int tempMj[], HU hu) {
		// int lvMj[7]={19,20,21,38,38,32};
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (MajHelper.IsWTSZ(hu.block[i].first)) {
				switch (hu.block[i].style) {
				case Constants.BLOCK_SUN:
				case Constants.BLOCK_CHI: {
					if (hu.block[i].first != 22) {
						return false;
					}
				}
					break;
				case Constants.BLOCK_PENG:
				case Constants.BLOCK_KE:
				case Constants.BLOCK_GANG:
				case Constants.BLOCK_BU_GANG:
				case Constants.BLOCK_AN_GANG: {
					if (hu.block[i].first == 22 || hu.block[i].first == 23
							|| hu.block[i].first == 24
							|| hu.block[i].first == 26
							|| hu.block[i].first == 28
							|| hu.block[i].first == 36) {

					} else {
						return false;
					}
				}
					break;
				default: {
					return false;
				}

				}
			}
		}
		if (hu.jiangMj == 22 || hu.jiangMj == 23 || hu.jiangMj == 24
				|| hu.jiangMj == 26 || hu.jiangMj == 28 || hu.jiangMj == 36) {
			return true;
		}
		return false;
	}

	// 万绿一点红
	public static boolean IsWanLvYiDianHong(int tempMj[], HU hu) {
		// 10,11,12,14,16,31
		boolean bZhong = false;
		if (hu.jiangMj == 35) {
			bZhong = true;
		}

		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_SUN:
			case Constants.BLOCK_CHI: {
				if (hu.block[i].first != 22) {
					return false;
				}
			}
				break;
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_BU_GANG:
			case Constants.BLOCK_AN_GANG: {
				if (hu.block[i].first == 35) {
					bZhong = true;
				} else {
					if (hu.block[i].first == 22 || hu.block[i].first == 23
							|| hu.block[i].first == 24
							|| hu.block[i].first == 26
							|| hu.block[i].first == 28) {

					} else {
						return false;
					}
				}
			}
				break;
			default: {
				return false;
			}

			}
		}
		if (bZhong) {
			if (hu.jiangMj == 22 || hu.jiangMj == 23 || hu.jiangMj == 24
					|| hu.jiangMj == 26 || hu.jiangMj == 28 || hu.jiangMj == 35) {
				return true;
			}
		}
		return false;
	}

	// 红孔雀
	public static boolean IsHongKongQue(int tempMj[], HU hu) {
		// 9,13,15,17,31
		boolean bZhong = false;
		if (hu.jiangMj == 35) {
			bZhong = true;
		}
		// int hongMj[7]={18,22,24,26,31};
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_PENG:
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_BU_GANG:
			case Constants.BLOCK_AN_GANG: {
				if (hu.block[i].first == 21 || hu.block[i].first == 25
						|| hu.block[i].first == 27 || hu.block[i].first == 29
						|| hu.block[i].first == 35) {

				} else {
					return false;
				}
			}
				break;
			default: {
				return false;
			}

			}
		}
		if (hu.jiangMj == 21 || hu.jiangMj == 25 || hu.jiangMj == 27
				|| hu.jiangMj == 29 || hu.jiangMj == 35) {
			return true;
		}
		return false;
	}

	// 百万石
	public static boolean IsBaiWanShi(int tempMj[], HU hu) {
		int total = 0;
		for (int i = 0; i < Constants.HAND_MJ_MAX; i++) {
			if (!IsWan(tempMj[i])) {
				return false;
			}
			total += tempMj[i];
		}
		if (total >= 100) {
			return true;
		}
		return false;
	}

	// 东北新干线
	// 一条龙，三个东风或北风，另一对做将
	public static boolean IsDongBeiXinGanXian(int tempMj[], HU hu) {
		if (!IsPaiXinYiQiTongGuan(tempMj, hu)) {
			return false;
		}
		if (hu.jiangMj != 31 && hu.jiangMj != 34) {
			return false;
		}
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			switch (hu.block[i].style) {
			case Constants.BLOCK_KE:
			case Constants.BLOCK_GANG:
			case Constants.BLOCK_BU_GANG:
			case Constants.BLOCK_AN_GANG: {
				if (hu.block[i].first == 31 || hu.block[i].first == 34) {
					return true;
				}
			}
			default:
				break;
			}
		}
		return false;
	}

	public static boolean IsDaCheLun(int tempMj[], HU hu) // 大车轮
	{
		int byDaCheLunMj[] = { 12, 12, 13, 13, 14, 14, 15, 15, 16, 16, 17, 17,
				18, 18 };
		if (Constants.memcmp(byDaCheLunMj, tempMj, Constants.HAND_MJ_MAX) == 0) {
			return true;
		}
		return false;
	}

	public static boolean IsShuangLongQiangZhu(int tempMj[], HU hu) // 双龙抢珠
	{
		if (IsTong(hu.jiangMj)) {
			for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
				if (hu.block[3].style != Constants.BLOCK_SUN) {
					return false;
				}
			}
			if (hu.block[0].first + 3 == hu.block[1].first
					&& hu.block[2].first + 3 == hu.block[3].first) {
				if (hu.block[0].first + 20 == hu.block[2].first) {
					return true;
				}
			}
		}
		return false;
	}

	public static int AdjustHu(int byHuType[]) {
		byHuType[Constants.TUI_DAO_HU] = 0;
		if (byHuType[Constants.QING_YI_SE] > 0) {
			byHuType[Constants.HUN_YI_SE] = 0;
		}
		// 大胡算番
		for (int i = 30; i < 50; i++) {
			if (byHuType[i] == 13) {
				return 13;
			}
			;
		}
		int iFanTotal = 0;
		for (int i = 0; i < 30; i++) {
			iFanTotal += byHuType[i];
		}
		if (iFanTotal == 0) {
			byHuType[Constants.TUI_DAO_HU] = 1;
			iFanTotal = 1;
		}
		return iFanTotal;
	}

	public static boolean IsDaHu(int byHuType[]) {
		// 大胡算番
		for (int i = 30; i < 50; i++) {
			if (byHuType[i] == 13) {
				return true;
			}
			;
		}
		return false;
	}

	public static boolean IsXiaoSanYuan(int tempMj[], HU hu) {
		if (IsSanYuan(hu.jiangMj) == false) {
			return false;
		}
		int total = 0;
		for (int i = 0; i < Constants.MAX_BLOCK_NUM; i++) {
			if (IsSanYuan(hu.block[i].first)) {
				total++;
			}
		}
		if (total == 2) {
			return true;
		}
		return false;
	}

	public static boolean IsDuTing(int tempMj[], HU hu, int byMj, int caiShen,
			ArrayList<HU> list) {
		int intstMj[] = new int[Constants.HAND_MJ_MAX];
		Constants.memcpy(intstMj, tempMj, Constants.HAND_MJ_MAX);

		for (int i = 0; i < list.size(); i++) {

			HU hu_s = list.get(i);
			if (hu_s.jiangMj != Constants.INVALID_CARD) {

				int cntTmpBlock = 0;
				int need_cs = 0;
				int testMj0 = hu_s.sanMj[0];
				int testMj1 = hu_s.sanMj[0] + 1;
				int testMj2 = hu_s.sanMj[0] + 2;
				BLOCK block0 = MajHelper.CheckBlock(hu_s.sanMj[0],
						hu_s.sanMj[0 + 1], testMj0);
				if (block0.style != Constants.BLOCK_NULL) {
					cntTmpBlock++;
					need_cs++;
				} else {
					BLOCK block1 = MajHelper.CheckBlock(hu_s.sanMj[0], testMj1,
							hu_s.sanMj[0 + 1]);
					if (block1.style != Constants.BLOCK_NULL) {
						cntTmpBlock++;
						need_cs++;
					} else {
						BLOCK block2 = MajHelper.CheckBlock(hu_s.sanMj[0],
								hu_s.sanMj[0 + 1], testMj2);
						if (block2.style != Constants.BLOCK_NULL) {
							cntTmpBlock++;
							need_cs++;
						} else {
							cntTmpBlock++;
							need_cs += 2;
						}
					}
				}
				if (need_cs == 1) {
					return true;
				}
			}
		}
		return false;
	}
}
